c # объявить переменную как интерфейс. почему это возможно? - PullRequest
2 голосов
/ 03 ноября 2011

Я не могу понять эту концепцию.

Если у меня есть этот интерфейс:

    public interface IValidate 
    {
       Dictionary<eValidationErrors, List<string>> ValidationMessages { get; }
     }

что произойдет, когда я скажу:

          var Validator = control as IValidate;
          Validator.ValidationMessages.Add(key,list);

Что такое Validator?Почему я могу использовать интерфейс таким образом?

Спасибо

Ответы [ 6 ]

5 голосов
/ 03 ноября 2011

Validator - это экземпляр типа, который реализует интерфейс IValidate (или ноль, если экземпляр control не реализует интерфейс IValidate).

Это полезно сделатьэто так, если вас не интересует фактическая или точная реализация определенного экземпляра, но если вы хотите использовать функции, предоставляемые интерфейсом.

Подумайте о некоторых методах в .NETСам фреймворк, который принимает параметр интерфейса - тип.Метод не заинтересован в самом типе;ему просто нужно убедиться, что переданный аргумент имеет определенные методы / свойства / etc ... объявленные указанным интерфейсом.

3 голосов
/ 03 ноября 2011

Оператор as преобразует правую часть в IValidate, поэтому Validator набирается как IValidate.

Другими словами, ваш код идентичен:

IValidate Validator = control as IValidate;

Ваш вопрос, похоже,

Почему я могу использовать интерфейс таким образом?

Но я не могу понять, почему вы думаете, что этот код будет вести себя по-другому. Возможно, разрыв в том, что вы еще не знакомы с использованием var в C #. Если так, то я уверен, что быстрое прочтение документации все прояснит.

Локальным переменным может быть присвоен логический «тип» var вместо явного типа. Ключевое слово var указывает компилятору выводить тип переменной из выражения в правой части оператора инициализации.

Обратите внимание, что нет никакой разницы в безопасности типов между var переменными и явно типизированными переменными.

1 голос
/ 03 ноября 2011

В любой данный момент либо Validator не будет содержать ничего (нулевое значение), либо экземпляр некоторого типа, который реализует IValidate, который может использоваться, как если бы он был экземпляром IValidate. Чтобы использовать пример, более похожий на абстрактные классы, но относящийся к тем же принципам, рассмотрим следующие запросы:

  1. Если Транспортное средство паркуется в этом месте с 18:00 до 8:00, буксируйте его.
  2. Принеси мне новый Автомобиль .

При условии, что у каждого Транспортного средства есть метод Tow (), тип Транспортного средства в первом запросе достаточно описательный, чтобы выполнить его. С другой стороны, тип Vehicle во втором методе слишком расплывчатый, чтобы его использовать. Не обязательно было бы предоставлять абсолютно полное описание объекта, который вы хотели, если бы вы предоставили тип, который имел параметры по умолчанию. Например, если указан ToyotaCamry, этот тип может иметь связанный по умолчанию год, цвет, стиль кузова, пакет опций и т. Д. С другой стороны, просто сказать, что кто-то хочет Vehicle , будет слишком открыто. закончился.

0 голосов
/ 03 ноября 2011

Интерфейсы обычно представляют протокол для связи с объектом. Поэтому, приведя объект к интерфейсу, вы соответствуете этому протоколу, и, таким образом, вы можете вызывать только его публично объявленных членов.

0 голосов
/ 03 ноября 2011

var означает, что тип будет иметь неявный тип.Важно понимать, что ключевое слово var не означает «вариант» и не указывает на то, что переменная свободно набрана или имеет позднюю привязку.Это просто означает, что компилятор определяет и назначает наиболее подходящий тип.

Так что если вы используете var Validator = control as IValidate;, тип Validator будет IValidate.

0 голосов
/ 03 ноября 2011

Вы можете использовать его как объект управления, реализующий IValidate. Следовательно, использование var возвращает интерфейсную часть этого объекта в Validator.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...