tags:

views:

124

answers:

4

I'm using an API that has a method that requires this type of argument:

System.Collections.ObjectModel.Collection<GenericTickType> genericTickList

How do I instantiate an object for that argument? Here's what I've tried but it keeps saying that the method call has some invalid arguments.

List<TickType> ticks_to_get = new List<TickType> { TickType.Price };

I've tried instantiating a Collection directly instead of a List and that doesn't seem to work.

+1  A: 

You can't pass a List<> as a Collection<>

Maybe you have problems with covariance/contravariance? You have to do the cast on your own:

List<TickType> ticks_to_get = new Collection<TickType> { TickType.Price };

genericTickList = (Collection<GenericTickType>) ticks_to_get;

Look at Dave Bauman's answer ... unless TickType.Price doesn't return an object of type TickType it will not work

EDIT: Since GenericTickType is an enum - which API are you using? Is it of your company - can you change it? It seems to be strange that you are asked to pass a collection of enum values. See, if you can change the enum to a flagged enum ... and then pass the required values by combining them with the or-operator.

tanascius
List<T> cannot be cast to a Collection<T>
Doanair
Yeah, I found it out, too - didn't test my code at first
tanascius
I get an error: Cannot convert type 'System.Collections.Generic.List<TickType>' to 'System.Collections.ObjectModel.Collection<GenericTickType>'
Dave
A: 

You can't use {} to initialize a Collection. You can do something like this, however:

List<TickType> ticks_to_get = 
    new List<TickType>( new TickType[] { TickType.Price });

or

List<TickType> ticks_to_get = new List<TickType>();
ticks_to_get.Add(TickType.Price);
Dave Bauman
You can, as show in my example, on the 3.5 framework.
Doanair
Actually, it's in C# 3.0, e.g. VS2008 targetting fx 2.0
Lucas
+1  A: 

What is the type of GenericTickType? Is it an enum or class? I am assuming enum. If that is the case, modify your code as such:

Collection<GenericTickType> ticks_to_get = new Collection<GenericTickType>() { GenericTickType.Price };

The above works on 3.5 framework.

Doanair
It's an enum. The solution you provided gives me the same error message as the original.
Dave
Yes, you can't cast a enum of type TickType to one of type GenericTickType.
tanascius
Right. You would have to use GenericTickType instead of TickType. it is an invalid cast. I can revise.
Doanair
+2  A: 

"I've tried instantiating a Collection directly instead of a List and that doesn't seem to work."

What error do you get? You can definitely create an instance of Collection<T> directly, it is not an abstract class and it has several public constructors, including one that's parameter-less. You can do this, for example:

var values = new System.Collections.ObjectModel.Collection<int> { 1,2,3,4 };

I noticed your sample code has a GenericTickType and a TickType. Is this a mistake or do you actually have two classes? You said it's an enum (which one?), so one cannot possibly derive from the other. If they are two enum types, Collection<GenericTickType> and Collection<TickType> are two different classes and one is not assignable to the other.

Now, if TickType is castable to GenericTickType (and they probably are if they are both enums, and assuming they share the same numeric values), you still cannot cast Collection<TickType> to Collection<GenericTickType>. There's no contra/co-variance in C# for most classes yet (coming in C# 4). But you could cast each TickType by doing something like this:

List<GenericTickType> list = new List<GenericTickType> { (GenericTickType)TickType.Price };
list.Add((GenericTickType)TickType.Price); // add more...
Collection<GenericTickType>genericTicks = new Collection<GenericTickType>(list);

If you already have a List<TickType> and have access to C# 3.0 and LINQ, you can do this:

List<TickType> ticks = new List<TickType> { TickType.Price };
list.Add(TickType.Price); // add more...
List<GenericTickType> castedList = ticks.Cast<GenericTickType>().ToList();
Collection<GenericTickType>genericTicks = new Collection<GenericTickType>(castedList);

This uses the LINQ Cast<T>() and ToList<T>() extension methods to cast each TickType in the original list to GenericTickType and creating a new List<GenericTickType> which is used to instantiate the Collecion<GenericTickType>. (I avoided using var so you could see the types in each step).

Lucas