Type constraints classes and interfaces

suggest change

Type constraints are able to force a type parameter to implement a certain interface or class.

interface IType;
interface IAnotherType;

// T must be a subtype of IType
interface IGeneric<T>
    where T : IType
{
}

// T must be a subtype of IType
class Generic<T>
    where T : IType
{
}

class NonGeneric
{
    // T must be a subtype of IType
    public void DoSomething<T>(T arg)
        where T : IType
    {
    }
}

// Valid definitions and expressions:
class Type : IType { }
class Sub : IGeneric<Type> { }
class Sub : Generic<Type> { }
new NonGeneric().DoSomething(new Type());

// Invalid definitions and expressions:
class AnotherType : IAnotherType { }
class Sub : IGeneric<AnotherType> { }
class Sub : Generic<AnotherType> { }
new NonGeneric().DoSomething(new AnotherType());

Syntax for multiple constraints:

class Generic<T, T1>
    where T : IType 
    where T1 : Base, new()
{
}

Type constraints works in the same way as inheritance, in that it is possible to specify multiple interfaces as constraints on the generic type, but only one class:

class A { /* ... */ }
class B { /* ... */ }

interface I1 { }
interface I2 { }

class Generic<T>
    where T : A, I1, I2
{
}

class Generic2<T>
    where T : A, B //Compilation error
{
}

Another rule is that the class must be added as the first constraint and then the interfaces:

class Generic<T>
    where T : A, I1
{
}

class Generic2<T>
    where T : I1, A //Compilation error
{
}

All declared constraints must be satisfied simultaneously for a particular generic instantiation to work. There is no way to specify two or more alternative sets of constraints.

Feedback about page:

Feedback:
Optional: your email if you want me to get back to you:


Generics:
* Type constraints classes and interfaces

Table Of Contents
17 Regex
19 Arrays
21 Enum
22 Tuples
24 GUID
27 Looping
36 Casting
46 Methods
57 Generics
88 Events
92 Structs
104 Indexer
106 Stream
107 Timers
109 Threading
127 Caching
135 Pointers
147 C# Script