Я всегда придерживался мнения, что свойства (т. Е. Их операции set / get) должны быть быстрыми / немедленными и безошибочными. Вы никогда не должны пытаться поймать или установить собственность.
Но я смотрю на некоторые способы применения безопасности на основе ролей к свойствам некоторых объектов. Например, свойство Employee.Salary. Некоторые из решений, с которыми я столкнулся, которые пробовали другие (в частности, пример AOP здесь ), включают создание исключения, если средство доступа не имеет необходимых разрешений - но это идет вразрез с личным правилом, которое у меня было в течение длительного времени.
Поэтому я спрашиваю: я не прав? Изменились ли вещи? Было ли принято, что свойства должны иметь возможность генерировать исключения?
.net
exceptions
Стивен Эверс
источник
источник
Ответы:
когда вы устанавливаете значение свойства, выдается исключение для недопустимого значения.
получение значения свойства не должно (почти) никогда генерировать исключение
для доступа на основе ролей используйте разные / более тупые интерфейсы или фасады; не позволяйте людям видеть то, что они не могут иметь!
источник
Я считаю, что это в основном дурной тон, но даже Microsoft рекомендует иногда использовать исключения. Хорошим примером является абстрактное свойство Stream.Length . В соответствии с рекомендациями, я бы больше заботился о том, чтобы избежать побочных эффектов для геттеров и ограничить побочные эффекты для сеттеров.
источник
Я бы определенно утверждал, что в дизайне есть недостаток, если вы чувствуете необходимость генерировать исключения из установщика или получателя свойства.
Свойство - это абстракция, представляющая нечто, представляющее собой просто значение . И вы должны иметь возможность устанавливать значение, не опасаясь, что это может вызвать исключение. *
Если установка свойства приводит к побочному эффекту, то это должно быть реализовано как метод. И если это не приводит к каким-либо побочным эффектам, то не должно быть никаких исключений.
Одним из примеров, уже упомянутых в другом ответе, является
Stream.Position
свойство. Это вызывает побочные эффекты и может создавать исключения. Но этот установщик свойств - просто оболочка,Stream.Seek
которую вы можете вызвать вместо этого.Лично я считаю, что позиция не должна была быть записываемой собственностью.
Другой пример, когда вы можете испытать искушение вызвать исключение из установщика свойства, в проверке данных:
Но есть лучшее решение этой проблемы. Введите тип, представляющий действительный адрес электронной почты:
В
Email
гарантирует , что класс не может иметь значение, которое не является действительным адресом электронной почты, и классы , которые нужно хранить электронные письма освобождаются от обязанности проверки их.Это также приводит к большей сплоченности (показатель хорошего дизайна программного обеспечения) - знание о том, что такое адрес электронной почты и как он проверяется, существует только в
Email
классе, который имеет только эту проблему.* ObjectDisposedException - единственное допустимое исключение (без каламбура), о котором я могу думать в данный момент.
источник
Я знаю, что ваш вопрос относится к .NET , но поскольку C # делится историей с Java, я подумал, что вас это может заинтересовать. Я не в коем случае , подразумевая , что , потому что что - то делается в Java, это должно быть сделано в C #. Я знаю, что они очень разные, особенно в том, что в C # значительно улучшена поддержка свойств на уровне языка. Я просто даю некоторый контекст и перспективу.
Из спецификации JavaBeans :
Возьми все это с крошкой соли, пожалуйста. Спецификация JavaBeans устарела, а свойства C # (IMO) - огромное улучшение по сравнению со свойствами, основанными на «соглашении об именовании», которые есть в Java. Я просто пытаюсь дать немного контекста, вот и все!
источник
Точкой свойства является принцип унифицированного доступа , то есть значение должно быть доступно через один и тот же интерфейс, независимо от того, реализовано ли оно с помощью хранилища или вычислений. Если ваше свойство выдает исключение, которое представляет собой состояние ошибки вне контроля программиста, то есть того типа, который должен быть перехвачен и обработан, вы заставляете своего клиента знать, что значение получается с помощью вычислений.
С другой стороны, я не вижу никаких проблем с использованием утверждений или подобных утверждений исключений, которые предназначены для того, чтобы сигнализировать о неправильном использовании API программисту, а не быть пойманными и обработанными. В этих случаях правильный ответ с точки зрения пользователя API состоит не в обработке исключения (таким образом, неявно заботясь о том, получено ли значение с помощью вычислений или хранения). Он должен исправить его / ее код, чтобы объект не оказался в недопустимом состоянии, или заставить вас исправить свой код, чтобы утверждение не сработало.
источник
AFAIK, это руководство главным образом исходит из мыслительного процесса, что свойства могут в конечном итоге использоваться во время разработки . (Например, свойство Text в TextBox) Если свойство бросает исключение, когда дизайнер пытается получить к нему доступ, у VS не будет хорошего дня. Вы получите кучу ошибок, просто пытаясь использовать конструктор, а для дизайнеров пользовательского интерфейса они не будут отображаться. Это также относится и ко времени отладки, хотя в сценарии исключений вы увидите просто «Исключение xxx», и оно не сработает VS IIRC.
Для POCO это не принесет никакого вреда, но я все еще уклоняюсь от того, чтобы сделать это сам. Я полагаю, что люди захотят получать доступ к свойствам чаще, поэтому они обычно должны быть дешевыми. Свойства не должны выполнять работу методов, они должны просто получать / устанавливать некоторую информацию и делать это с общим правилом.
источник
Хотя многое будет зависеть от контекста, я бы вообще не использовал в своих свойствах любую ломкую логику (включая исключения). Как один из примеров, есть много вещей, которые вы (или какая-либо библиотека, которую вы используете) могли бы сделать, используя отражение для перебора свойств, что приводило к ошибкам, которые вы не ожидали во время разработки.
Я говорю в целом, хотя, поскольку могут быть случаи, когда вы абсолютно определенно хотите заблокировать что-то, не слишком заботясь о последствиях. Безопасность, я думаю, будет классическим случаем там.
источник