I have a method that asks for a type <T>
. It only requires that this type have a Count
property defined. How can I specify that as a type constraint that allows all objects for which Count
is defined?
This is what I have currently:
private static void writeData<T>(String fileName, T rawData) where T : ICollection
However, this won't work if I try to use it with an IDictionary
. What else can I try?
Update: I think the problem开发者_如何学Go is that I'm constraining it to the non-generic ICollection
, instead of the generic ICollection<E>
.
Your code should work with an IDictionary
, since it implements ICollection
.
Note that it will not work with an IDictionary<TKey, TValue>
, since it doesn't implement (non-generic-) ICollection
.
If you want to accept generic collections, you can change it to
static void WriteData<TElement>(String fileName, ICollection<TElement> rawData)
By the way, you don't actually need to use generics here; you can just take a parameter of type ICollection
, and callers can pass any derived type.
To take generic collections, you'll need a type parameter for the element, but not for the collection type.
To answer your other question, you cannot constrain a parameter by the existence of a property, except by making an interface.
Since there is no ICountedEnumerable
interface in the framework, you're out of luck there. (Unless you make your own interface and only allow custom collections that implement it)
I don't think you can do this at compile time.
You can use reflection to check if T has a Count method and then invoke it.
in response to update: Then don't pass the dictionary. Pass the dictionaryVariable.Values
instead.
You are looking for something called structural typing. (The accepted solution, while perhaps valid/appropriate, does not utilize structural typing.)
See (the SO question) Does C# have an equivalent to Scala's structural typing?.
The short answer appears to be "no" although some duck-typing approaches are possible.
精彩评论