В C# компилятор будет выбрать правильный метод в зависимости на объявленном типе переменной, а не на фактическом типе, хранящемся в нем.
Обратите внимание, что приведенный ниже код объявляет W
классом и создает его экземпляр. Если вы сделаете W
интерфейсом и удалите его декларацию и конструкцию, вы получите то же поведение для x
и y
, так как программа ниже, интерфейс или класс для W
в этом случае не имеет значения.
Позвольте мне показать вам разницу:
using System;
namespace SO2851194
{
class W { }
class X : W { }
class Y : W { }
class Program
{
static void Main()
{
W w = new W();
X x = new X();
Y y = new Y();
doSomething(w);
doSomething(x);
doSomething(y);
}
static void doSomething(W w)
{
Console.Out.WriteLine("w");
}
static void doSomething(X x)
{
Console.Out.WriteLine("x");
}
}
}
Здесь я объявляю три переменные типа W
, X
и Y
и вызвать doSomething
проходя три переменные, один за другим. Вывод этой программы:
w
x
w
Как и следовало ожидать, компилятор будет выбрать метод, который имеет наиболее подходящий тип параметра, и в случае переменную x
, то есть метод, который может принимать объект тип X
.
Однако из-за наследования класса, мы можем изменить объявление переменных, но сохранить типы объектов, сконструированных, поэтому изменение кода:
W w = new W();
W x = new X(); // Notice, changed variable type to W
W y = new Y(); // but keep constructing X and Y
Теперь это выводит:
w
w
w
Так что тот факт, что переменная x
содержала объект типа X
, не учитывала его, компилятор выбрал метод из типа переменной, а не его содержимого.
В C# 4.0, теперь у вас есть dynamic
тип, поэтому снова изменить код, чтобы:
dynamic w = new W();
dynamic x = new X();
dynamic y = new Y();
снова выводит:
w
x
w
, как теперь компилятор откладывает сбор какой-либо метод вообще до runtime, и во время выполнения он видит, что переменная с именем x
фактически содержит объект типа X
, а затем выбирает метод с наилучшим подходящим типом параметра.
Вы можете быть более конкретным? Вы имеете в виду проблему с алмазом или что-то еще? – wheaties
это, вероятно, зависит от рассматриваемого языка программирования, но, как правило, компилятор выбирает метод, который имеет наиболее подходящий тип параметра, в этом случае тот, который принимает объект «x». –
Почему бы вам не попробовать? Ничего плохого с тобой не случится. :) – Simon