Search code examples
c#genericsparametersrestrictions

Restrict generic parameter on interface to subclass


The following is contrived, but bear with me:

interface Clonable<TSubClass>
{
    TSubClass Clone();
}

How can I restrict TSubClass to be of the implementing type?

i.e only let the implementor do this:

class Dog : Clonable<Dog>
{
    Dog Clone() 
    {
        ....
    }
}

Not this:

class BadDog : Clonable<Rabbit>
{
    Rabbit Clone()
    {
        ....
    }
}

Solution

  • You can't enforce that at compile-time, because .NET generics don't have template specialization or duck typing.

    You can, however, include a static constructor (type initializer) that uses reflection to assert the relationship at load time. Ok, C# doesn't allow you to put a static constructor on an interface (even though .NET does allow it), so you would need to use a module initializer or a function you call yourself. Also, you would need to search for types implementing the interface, including types that aren't loaded yet (you can subscribe to the Assembly.Load event to be notified of types loaded in the future).