Home > Mobile >  Event using a generic type constraint to a delegate
Event using a generic type constraint to a delegate

Time:12-14

I was trying to implement (in C#8.0) a class with a generic type parameter (constraint to a delegate) having an event parameter with the same generic type. The intended purpose is to have some custom event handling (Subscribe & Unsubscribe functions) while still allowing any kind of delegate associated with it.

public class AEvent<T> where T : Delegate
{
    private event T eventData;

    public AEvent() { }
}

Starting out with the code above, the IDE gives me this error:

'eventData': event must be of a delegate type

Can someone explain briefly why can't I implement this? Or if there's any alternative way of achieving this?

CodePudding user response:

The C# specification explicitly states this is not allowed (my bold)

Events

The type of an event declaration must be a delegate_type ....

Delegates

The only way to declare a delegate type is via a delegate_declaration. A delegate type is a class type that is derived from System.Delegate. ...snip... Note that System.Delegate is not itself a delegate type; it is a class type from which all delegate types are derived.

As mentioned by others, it doesn't make a huge amount of sense to do this anyway. Whatever you do, and however you generify this, you have no way of specifying the arity (how many parameters to pass), so you would not be able to call it.

Your best bet is to use Action<T> or EventHandler<TEventArgs>, that way you at least know the number of parameters, and can use generics for the rest.

CodePudding user response:

How will you rise the event? You don't know if the delegate requires arguments and how many and of which type. I would use classes AEvent, AEvent<T>, AEvent<T1,T2> etc. and declare the events using Action, Action<T> and Action<T1,T2> respecitvely.

public class AEvent
{
    private event Action eventData;
}

public class AEvent<T>
{
    private event Action<T> eventData;
}

public class AEvent<T1, T2>
{
    private event Action<T1, T2> eventData;
}

...
  • Related