I'm trying to create a new object of type T via its constructor when adding to the list.
I'm getting a compile error: The error message is:
'T': cannot provide arguments when creating an instance of a variable
But my classes do have a constructor argument! How can I make this work?
public static string GetAllItems<T>(...) where T : new()
{
...
List<T> tabListItems = new List<T>();
foreach (ListItem listItem in listCollection)
{
tabListItems.Add(new T(listItem)); // error here.
}
...
}
Since nobody bothered to post the 'Reflection' answer (which I personally think is the best answer), here goes:
Edit: This answer is deprecated due to .NET 3.5's Activator.CreateInstance, however it is still useful in older .NET versions.
This is kind of mucky, and when I say kind of mucky I may mean revolting, but supposing you can furnish your parameterised type with an empty constructor, then:
Will effectively allow you to construct an object from a parameterised type with an argument. In this case I am assuming the constructor I want has a single argument of type
object
. We create a dummy instance of T using the constraint permitted empty constructor and then use reflection to get one of its other constructors.Object initializer
If your constructor with the parameter isn't doing anything besides setting a property, you can do this in C# 3 or better using an object initializer rather than calling a constructor (which is impossible, as has been mentioned):
Using this, you can always put any constructor logic in the default (empty) constructor, too.
Activator.CreateInstance()
Alternatively, you could call Activator.CreateInstance() like so:
Note that Activator.CreateInstance can have some performance overhead that you may want to avoid if execution speed is a top priority and another option is maintainable to you.
Very old question, but new answer ;-)
The ExpressionTree version: (I think the fastests and cleanest solution)
Like Welly Tambunan said, "we could also use expression tree to build the object"
This will generate a 'constructor' (function) for the type/parameters given. It returns a delegate and accept the parameter types as an array of objects.
Here it is:
Example MyClass:
Usage:
Another example: passing the types as an array
DebugView of Expression
This is equivalent to the code that is generated:
Small downside
All valuetypes parameters are boxed when they are passed like an object array.
Simple performance test:
Results:
Using
Expressions
is +/- 8 times faster than Invoking theConstructorInfo
and +/- 20 times faster than using theActivator
I believe you have to constraint T with a where statement to only allow objects with a new constructor.
RIght now it accepts anything including objects without it.
In order to create an instance of a generic type in a function you must constrain it with the "new" flag.
However that will only work when you want to call the constructor which has no parameters. Not the case here. Instead you'll have to provide another parameter which allows for the creation of object based on parameters. The easiest is a function.
You can then call it like so