If I have a generic class:
public class MyClass<T> { public T Value; }
I want to instantiate several items such as...
new MyClass<string> new MyClass<int>
...and add them to a collection. How do I define the collection so that it can hold a list of generic types? I then want to iterate through the collection at some point, and use the Value property. Possible?
The generic collections disable the type-casting and there is no use of type-casting when it is used in generics. The generic collections are type-safe and checked at compile-time. These generic collections allow the datatypes to pass as parameters to classes.
A generic collection is strongly typed (you can store one type of objects into it) so that we can eliminate runtime type mismatches, it improves the performance by avoiding boxing and unboxing.
Generic classes are used to provide the type safe structure -- type safe means only one type of data can be contained within Generic classes. The data type is defined at the time of an object initialization. We can have a different type of collection.
Have your generic class inherit from a non-generic base, or implement a non-generic interface. Then you can have a collection of this type and cast within whatever code you use to access the collection's contents.
Here's an example.
public abstract class MyClass { public abstract Type Type { get; } } public class MyClass<T> : MyClass { public override Type Type { get { return typeof(T); } } public T Value { get; set; } } // VERY basic illustration of how you might construct a collection // of MyClass<T> objects. public class MyClassCollection { private Dictionary<Type, MyClass> _dictionary; public MyClassCollection() { _dictionary = new Dictionary<Type, MyClass>(); } public void Put<T>(MyClass<T> item) { _dictionary[typeof(T)] = item; } public MyClass<T> Get<T>() { return _dictionary[typeof(T)] as MyClass<T>; } }
The only way I can think of, off the top of my head is as follows (wrapped up in a Console app for testing):
class Program { static void Main(string[] args) { var x = new MyClass<string>() { Value = "34" }; var y = new MyClass<int>() { Value = 3 }; var list = new List<IMyClass>(); list.Add(x); list.Add(y); foreach (var item in list) { Console.WriteLine(item.GetValue); } } private interface IMyClass { object GetValue { get; } } private class MyClass<T> : IMyClass { public T Value; public object GetValue { get { return Value; } } } }
i.e. Have MyClass implement an empty interface and then create your collections as one that holds instances of classes that implement that interface.
Update: I've added a "GetValue" method to the interface that allows you to access the "Value" of the MyClass instance as an Object. This is about as good as it's going to get, afaik, if you want to have a collection that holds mixed types.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With