- •Функции
- •Определение и использование функций Определение и использование базовой функции базовой функции
- •Перегрузка функций
- •Делегаты
- •Применение делегата для вызова функции
- •Классы Определение классов в с#
- •Определение членов
- •Конструкторы и деструкторы
- •Последовательность выполнения конструкторов
- •Интерфейсы
- •Реализация интерфейсов
- •Реализация интерфейсов в классах
- •Наследование
- •Полиморфизм
- •Полиморфизм интерфейсов
Интерфейсы
Интерфейс (interface) — это коллекция общедоступных методов и свойств, которые объединяются вместе для инкапсуляции конкретной функциональности. После определения интерфейса его можно реализовать в классе. Это означает, что в таком случае класс будет поддерживать все свойства и члены, специфицируемые данным интерфейсом.
Важно обратить внимание на то, что интерфейсы не могут существовать сами по себе. Создавать "экземпляр" интерфейса, как это можно делать с классом, нельзя. Помимо этого, интерфейсы не могут содержать никакого кода, реализующего их члены, они могут лишь определять их, а реализоваться те должны непосредственно в классах, которые реализуют данный интерфейс.
Допустим в классе чашка кофе CupOfCoffee многие из свойств и методов более общего назначения, вроде AddSugar (), Milk, Sugar и Instant, можно было бы сгруппировать вместе в интерфейс, назвать его, скажем, IHotDrink (Горячий напиток) (имена интерфейсов обычно сопровождаются префиксом в виде заглавной буквы I), и применять для других объектов, например, объектов класса CupOfTea (Чашка чая). Это позволило бы работать со всеми этими объектами похожим образом и при этом все равно разрешить им иметь свои собственные свойства (например, объектам CupOfCoffee - свойство ВеаnТуре (Сорт кофейных зерен), а объектам CupOfTea -свойство LeafТуре (Сорт чайных листьев)).
Интерфейсы, реализуемые для объектов, в UML изображаются с использованием синтаксиса в форме окружности с линией На рис. члены интерфейса IHotDrink вынесены в отдельный прямоугольник и перечислены с использованием подобного классам синтаксиса.
Рис. Представление интерфейсов в UML
Один класс может поддерживать несколько интерфейсов, а несколько классов могут поддерживать один и тот же интерфейс. Следовательно, интерфейсы позволяют упрощать жизнь для пользователей и других разработчиков. Например, предположим, что есть некий код, в котором используется объект с определенным интерфейсом. Если не использовать другие свойства и методы этого объекта, один объект можно будет легко заменять другим (приводившийся ранее код, в котором использовался интерфейс IHotDrink, например, мог работать как с экземплярами CupOfCoffee, так и с экземплярами CupOfТea). Кроме того, сам разработчик данного объекта может выпустить его обновленную версию, и при условии, что она поддерживает находящийся в эксплуатации интерфейс, другой разработчик сможет легко применить новую версию в своем коде.
После публикации интерфейса, т.е. предоставления к нему доступа другим разработчикам или конечным пользователям, рекомендуется не изменять его. Можно представить, что интерфейс является своего рода контрактом между создателями класса и его потребителями, в котором создатели, по сути, заявляют, что каждый класс, поддерживающий интерфейс X, будет поддерживать такие-то методы и свойства. Если интерфейс позже изменится, например, в результате модернизации лежащего в основе кода, это может привести к тому, что его потребители больше не смогут работать с ним корректным образом или вообще утратят возможность запускать его. Поэтому вместо этого рекомендуется создавать новый интерфейс, расширяющий возможности старого и имеющий, например, такой номер версии, как Х2. Такой подход уже стал стандартным, поэтому интерфейсы с пронумерованными версиями встречаются довольно часто.