День двести шестьдесят восьмой. #ЗаметкиНаПолях
Нетривиальный пример использования явной реализации интерфейса
Про то, что такое явная реализация интерфейса, я писал достаточно давно. Однако на днях попался интересный пример использования, который захотелось записать на будущее.
Когда класс реализует интерфейс, он обязан содержать методы с сигнатурами, которые соответствуют указанным в интерфейсе. Вы можете использовать явную реализацию интерфейса, чтобы сделать методы, реализующие интерфейс, видимыми только тогда, когда к объекту обращаются через интерфейсную ссылку.
Например, вы можете создать интерфейс
Следующий код показывает класс
Таким образом можно спрятать методы, не относящиеся непосредственно к функционалу класса. Потребители класса-отчёта (кроме принтера) не смогут использовать эти методы, т.к. они им не нужны. Более того, используя частичные (
Источник: Rob Miles “Exam Ref 70-483 Programming in C#”. 2nd ed - Pearson Education, Inc., 2019. Глава 2.
Нетривиальный пример использования явной реализации интерфейса
Про то, что такое явная реализация интерфейса, я писал достаточно давно. Однако на днях попался интересный пример использования, который захотелось записать на будущее.
Когда класс реализует интерфейс, он обязан содержать методы с сигнатурами, которые соответствуют указанным в интерфейсе. Вы можете использовать явную реализацию интерфейса, чтобы сделать методы, реализующие интерфейс, видимыми только тогда, когда к объекту обращаются через интерфейсную ссылку.
Например, вы можете создать интерфейс
IPrintable
, который определяет методы, используемые для печати любого объекта. Это хорошая идея, потому что теперь у принтера можно попросить напечатать любой объект класса, реализующего IPrintable
. Если подумать, то методы интерфейса IPrintable
имеют смысл только тогда, когда они используются чем-то, пытающимся напечатать объект. Не имеет смысла вызывать методы печати в каком-либо ином контексте, кроме как через ссылку на IPrintable
. Этого можно добиться, сделав реализацию методов печати явной, то есть добавив имя интерфейса к объявлению тела метода.Следующий код показывает класс
Report
, который реализует интерфейс IPrintable
. Класс Report
содержит два метода: GetPrintableText
и GetTitle
, которые объявлены в интерфейсе IPrintable
. interface IPrintableТеперь единственный способ получить доступ к этим методам в экземпляре отчёта – приведя отчёт к
{
string GetPrintableText(int page);
string GetTitle();
}
class Report : IPrintable
{
string IPrintable.GetPrintableText(int page)
{
return "Текст отчёта";
}
string IPrintable.GetTitle()
{
return "Заголовок отчёта";
}
}
IPrintable
. На рисунке ниже показан эффект в Visual Studio: методы GetPrintableText
и GetTitle
скрыты от IntelliSense, если обращаться через класс Report
напрямую, но при обращении через IPrintable
они видны.Таким образом можно спрятать методы, не относящиеся непосредственно к функционалу класса. Потребители класса-отчёта (кроме принтера) не смогут использовать эти методы, т.к. они им не нужны. Более того, используя частичные (
partial
) классы, можно и сам код этих методов вынести в отдельный файл, чтобы он не загромождал код основного функционала.Источник: Rob Miles “Exam Ref 70-483 Programming in C#”. 2nd ed - Pearson Education, Inc., 2019. Глава 2.