Downcasting Lists [duplicate]
Possible Du开发者_运维知识库plicate:
In C#, why can't a List<string> object be stored in a List<object> variable
Say that you have a class that triggers events with collections of different classes. You want to take those collections and instantiate an object that takes a List<object> as parameter to it's constructor (you need the methods of IList: indexed accessed, indexOf etc).
What is the best practice?
If the events return List or IList you have to do some nasty casting when creating it from a List of a more specific class, say List<SomeClass> because IList is invariant.
new DataObject(someClasses.Cast<object>().ToList())
You can use Enumerable<whatever> in the events, then at least you can simply do new DataObject(someClasses.ToList()) but a new List still has to be created which might have some overhead...
It seems a little weird that Lists can't be downcasted to object automatically
The problem is your methods that take List<object>
as a parameter. Options:
- Make them take
IEnumerable<object>
- Make them generic, taking
List<T>
Here's why you can't convert (say) a List<string>
to a List<object>
:
List<string> strings = new List<string>();
List<object> objects = strings;
objects.Add(new Button());
string text = strings[0];
Clearly that can't "work" at execution time, so it's better that it's prohibited at compile time. Lines 1, 3 and 4 all look fine to me - so it's got to be line 2 that causes the problem, which indeed is the way the language is designed. How would you suggest the language could have been designed to make the above "safe"?
For a lot more about generic variance, see my NDC 2010 talk on the topic - go to the NDC video page and search for "variance".
精彩评论