В настоящее время я готовлю презентацию новых общих функций дисперсии в C # для моих коллег. Короче говоря, я написал следующие строки:
IList<Form> formsList = new List<Form> { new Form(), new Form() };
IList<Control> controlsList = formsList;
Да, это, конечно, невозможно, так как IList (Of T) инвариантен (по крайней мере, моя мысль). Компилятор говорит мне, что:
Невозможно неявно преобразовать тип
System.Collections.Generic.IList<System.Windows.Forms.Form>
до
System.Collections.Generic.IList<System.Windows.Forms.Control>
.
существует явное преобразование (вам не хватает приведения?)
Хм, значит ли это, что я могу форсировать явное преобразование? Я только что попробовал:
IList<Form> formsList = new List<Form> { new Form(), new Form() };
IList<Control> controlsList = (IList<Control>)formsList;
И ... он компилируется! Значит ли это, что я могу отбросить инвариантность? - По крайней мере с компилятором все в порядке, но я просто превратил предыдущую ошибку времени компиляции в ошибку времени выполнения:
Unable to cast object of type 'System.Collections.Generic.List`1[System.Windows.Forms.Form]' to type 'System.Collections.Generic.IList`1[System.Windows.Forms.Control]'.
Мой вопрос (ы): Почему я могу отбросить инвариантность IList<T>
(или любого другого инвариантного интерфейса в отношении моих экспериментов)? Действительно ли я отбрасываю инвариантность, или какое преобразование происходит здесь (поскольку IList(Of Form)
и IList(Of Control)
совершенно не связаны)? Это темный угол C #, я не знал?