How could I declare list of generics with different and unknown types and How could I initialize a generic with a type only known at runtime?

This is a 2 part question.

Firstly I have a class called ComponentList that looks like this:

public class ComponentList<T> : List<T> where T : Component
{

}

Now I want to create an empty list of typeless ComponentLists:

List<ComponentList<>> MasterList = new List<ComponentList<>>();

I get an error because the ComponentList wants a generic type specified even though I'm not trying to initialize any ComponentLists yet (just the MasterList that contains them). How would I declare the MasterList of ComponentLists without initializing any ComponentLists (as I plan to initialize them during runtime with types only known at runtime)? After all, the MasterList needs to contain ComponentLists of different generic types, not just one.

Secondly I know this one has been asked before, but I can't seem to wrap my head around the concepts of any of the proposed solutions.

As you know, I have a List<> called MasterList which is a list of ComponentLists (a custom class). A ComponentList is a generic class of an undefined type (that is constrained to being a subtype of Component).

In the following example, I'm trying to check if a ComponentList generic type (referenced from MasterList) is the same as this class (the class the code's being called from).

if (MasterList[i].GetType() == typeof(ComponentList<this.GetType()>))
{

}

Problem is, the code is meant to be automatically called from unknown child classes, not from this parent class. So the ComponentList generic type needs to be compared with the type of the child class, not this base class. Hence the "this.GetType" inplace of what would be the hardcoded name of the actual base class.

The this.GetType() type passed in the ComponentList<> returns a "type expected" error apparently because GetType() returns compile time type, not runtime type (which is what I need).

So how could I get the runtime type? And if I can't, what would be the best alternative to accomplishing what I'm trying to do? (I've heard a bit about something called reflections that might help me but I really don't understand).

Answers


You cannot determine generic types at runtime. C# (all .Net, actually) is designed that way on purpose. The compiler treats a generic type virtually same way as an explicitly defined type.

Consider the following:

class MyGenericClass<T>
{
    public static T MyProperty { get; set; }
}

class MyIntClass
{
    public static int MyProperty { get; set; }
}

class UseThem
{
    public void test()
    {
        // both are JIT'ed to be exactly the same machine code
        var foo = MyGenericClass<int>.MyProperty;
        var bar = MyOtherClass.MyProperty;
    }
}

Thus, you must provide a type for the generic class so that JIT knows what to compile.

Possible Alternative If all of the possible types which could possible end up being the generic type are similar (inherit from the same base class or implement a similar interface), then you can instantiate the generic class with an interface or base class as the generic type:

List<ComponentList<ComponentBase>> MasterList = new List<ComponentList<ComponentBase>>();
// -OR-
List<ComponentList<IMyComponent>> MasterList = new List<ComponentList<IMyComponent>>();

I have a hunch that you should be able to define a common interface or base class with a little creative refactoring. :)


Need Your Help

PHP password_verify seems to work with with one string but not another that is considered equal

php mysql hash passwords password-encryption

I am storing a username and an encrypted password in a mysql database. For testing only, I am also storing the password in an unencrypted form in the database as well.

Edit collectionViewCell

ios objective-c uicollectionview uicollectionviewcell collectionview

I'm trying to change a specific CollectionViewCell once it's tapped on. I created a custom cell:

About UNIX Resources Network

Original, collect and organize Developers related documents, information and materials, contains jQuery, Html, CSS, MySQL, .NET, ASP.NET, SQL, objective-c, iPhone, Ruby on Rails, C, SQL Server, Ruby, Arrays, Regex, ASP.NET MVC, WPF, XML, Ajax, DataBase, and so on.