Morten
Morten

Reputation: 3844

Create generic instance with delegate arg

I am trying to refactor some code by introducing generics, and I got stuck. I am trying to create a new instance of T, but the trouble is, that T has a delegate argument in the constructor. What I was aiming for was something like this:

public delegate IOrders DoStuffDelegate(); 


public class GenericBoss<T> where T:Worker
{

    public void DelegateWork()
    {
        T worker = Activator.CreateInstance(typeof(T), new[]{GiveOrders})
        worker.Work();
    }

    public IOrders GiveOrders()
    {
        return new OrderFromTheBoss();
    }
}

public class Worker
{
    private readonly DoStuffDelegate _takeOrders;

    public Worker(DoStuffDelegate takeOrders)
    {
        _takeOrders = takeOrders;
    }

    public void Work()
    {
        _takeOrders(); 
    }
}

However, this doesn't work, as only [object] types are allowed as arguments in the [Activator]. I am not allowed to change the constructor, so moving the delegate elsewhere is not possible.

Is there a way out, or is generics not an option here?

Regards, Morten

Upvotes: 2

Views: 1279

Answers (1)

Jon Skeet
Jon Skeet

Reputation: 1500375

The problem is that the compiler doesn't know which delegate you want to convert your method group to. If it's always the DoStuffDelegate, you can just do this:

object[] args = new object[] { new DoStuffDelegate(GiveOrders) };
T worker = (T) Activator.CreateInstance(typeof(T), args);

or

DoStuffDelegate giveOrders = GiveOrders;
object[] args = new object[] { giveOrders };
T worker = (T) Activator.CreateInstance(typeof(T), args);

If the delegate type is different for each T, it's harder - you'd probably need to call Delegate.CreateDelegate to create an instance of the appropriate delegate type, discovered via reflection :(

Upvotes: 3

Related Questions