Помните, что НИКАКИХ наследований или реализационных отношений нет между специализациями универсального типа. List<Foo>
никак не наследуется от List<IFoo>
. Это похоже на сравнение string
с int
.
Это не значит, что между типами вообще нет никакой связи; Просто эти отношения не являются наследством. Вместо этого у нас есть отношения специализация между двумя типами. Некоторые типы в .Net 4.0 и более поздних версиях поддерживают атрибут специализации, известный как ковариация . Совместная и противоречивая позволяют специализированной части универсального типа изменять (обратите внимание на коренное слово там) при определенных обстоятельствах List<T>
не относится к таким типам.
Но то, что я бы сделал в этом случае (где я точно не знаю, что у вас есть .Net 4.0), это сделал весь метод обобщенным:
public void MyMethod<T>(IEnumerable<T> items) where T : IFoo
{
//...
}
Обратите внимание, что я также использовал IEnumerable<T>
вместо List<T>
. Вы все еще должны иметь возможность передавать списки этой функции, потому что между IEnumerable<T>
и List<T>
существует отношение наследования / реализации. Вы также можете обрабатывать массивы и любые другие поддерживаемые последовательности. IEnumerable также является одним из типов, поддерживающих ковариацию. Почти любой метод, который требует аргумент List<T>
, должен быть обновлен, чтобы использовать вместо него IEnumerable<T>
.