Currently, there is a very large subset of C# language features that can not be used when using generics or interfaces:-operators-static properties-constructors with arguments-static methods-implicit conversionsWhen not using generics or interfaces, C# is a very powerful and flexible language. But once you start using generics or interfaces it is very restricted. This might be OK if you use generics only for typed collections, but as soon as you use generics for something else this becomes very painful. There are plenty of people that want to use C# generics for more than just typed collections. Just look at all the feedback items for "generic constructor", "generic static" or "generic operator". Unfortunately there is not a single common feedback item for this issue, so the importance of this feature is maybe overlooked. For example with the current generics system it is impossible to perform arithmetic calculations on generic classes without sacrificing performance by using some kind of dynamic dispatch, or having to use very ugly hacks such as having a separate "calculator" type.One solution would be to allow something like a structural type constraint similar to an interface constraint on type parameters. Here is a proposed syntax for specifying structural constraints. A new keyword "signature" is introduced. Inside a signature, everything is allowed that is allowed in a normal class/struct: static methods and fields, operators, type conversions, constructors with or without parameters etc. Of course you may not provide an implementation, since that is not part of the signature. signature Numeric { public static Numeric operator +(Numeric a, Numeric b); public static Numeric operator *(Numeric a, Numeric b); public static Numeric Zero { get; } public static Numeric One { get; } ...} Now that a signature is defined, it is possible to use it as a constraint similar to an interface constraint:public class Summer<T> where T:Numeric { public static T Sum(T[] items) { var result=T.Zero; foreach(var item in items) //this directly calls the + operator without any kind of dynamic dispatch //(interfaces or delegates), //so it is just as fast as using the concrete type directly, but more flexible result+=item; return result; }}public struct Complex<T> where T:Numeric{ readonly T re; readonly T im; ....}You get the idea.The difference to an interface constraint is that the concrete type does not have to explicitly implement the signature. Instead it just has to conform to the signature by implementing the right methods/operators/constructors/properties with the right parameters and return values. So for example System.Double would conform to a signature requiring a + operator without having to implement it. I realize that it is probably difficult to implement this feature since a new type would have to be generated for each T, so some changes to the CLR would be needed, just like the CLR generates a new type for each concrete struct T with an interface constraint. And there might be some resistance from OO purists since two classes might have a method with the same name, the same parameters and return value and yet a different meaning. However C# has many features (for example extension methods, lambda expressions etc.) that are definitely not pure OO. Besides, C# is being sold as a multiparadigm language. But something like this is definitely needed if C# wants to be a real alternative to C++ and not just a language for writing "business applications" and thin database frontends. The proposed solution is somewhat similar to the C++ template approach, yet since it is explicit it allows much better IDE integration such as intellisense and refactoring as well as better error messages when a type does not conform to a signature. If you can come up with something more clever than the solution I proposed, then by all means do it. But something needs to be done about this issue. IMHO this is way more important than adding support for dynamic invocation to C# since it permits an entire class of problems to be solved in C# that can only be solved in C++ as of now. So please don't tell me that you don't have time for this.
Version