Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Should generic constraints be preferred to using interfaces as parameter types?

Consider this trivial function:

public static bool IsPositive(IComparable<int> value)
{
    return value.CompareTo(0) > 0;
}

Now, if I pass an int to this method, it gets boxed. Wouldn't it therefore be better to define the above method as follows?

public static bool IsPositive<T>(T value) where T : IComparable<int>
{
    return value.CompareTo(0) > 0;
}

Using a generic constraint in this way, I can achieve exactly the same functionality as the code above, with the added benefit that no boxing is necessary (since a call to IsPositive<int> accepts a parameter of type int).

The example code above is clearly quite pointless. But my broader question is: wouldn't it always make sense to define methods in the latter way (using a generic constraint rather than having a parameter of some interface type), to avoid the potential boxing of value types?

I suspect that the answer is likely to be "yes, but it requires more typing and in many cases encountering a value type will be very unlikely, such as when a method accepts some IEnumerable<T>." But I'm wondering if there's a greater difference between these approaches that is escaping me at the moment.

like image 883
Dan Tao Avatar asked Aug 19 '10 20:08

Dan Tao


People also ask

What does the generic constraint of type interface do?

Interface Type Constraint You can constrain the generic type by interface, thereby allowing only classes that implement that interface or classes that inherit from classes that implement the interface as the type parameter.

What does the generic constraint of type interface do in C#?

C# allows you to use constraints to restrict client code to specify certain types while instantiating generic types. It will give a compile-time error if you try to instantiate a generic type using a type that is not allowed by the specified constraints.

What are generic constraints?

The where clause in a generic definition specifies constraints on the types that are used as arguments for type parameters in a generic type, method, delegate, or local function. Constraints can specify interfaces, base classes, or require a generic type to be a reference, value, or unmanaged type.

Can a generic class have multiple constraints?

Multiple interface constraints can be specified. The constraining interface can also be generic.


1 Answers

One issue would be with the fact that the generic constrain isn't really part of the signature. If you have ...

static T Method<T>(T value) where T : ICompareable<int>

... and ...

static T Method<T>(T value) where T : IEnumerable<int>

... the compiler wouldn't have a way to know which is which.

And to invoke Eric Lippert...

  • Constraints are not part of the signature

  • A Generic Constraint Question

like image 191
Matthew Whited Avatar answered Oct 24 '22 16:10

Matthew Whited