泛型类,泛型方法,泛型属性
1 | public class MyClass<T> |
MyClass是一个泛型类。
即使类不是泛型类,也可以定义泛型方法
1 | public class MyClass |
属性不能指定自己的泛型参数,它们只能使用所属类中定义的泛型参数进行操作。
1 | public class MyClass<T> |
泛型类的实例化
1 | var myClass=new MyClass<int>(); |
在调用泛型方法的时候,可以提供要在调用场所使用的类型
1 | //调用泛型方法 |
在调用泛型方法时,C#编译器足够聪明,基于传入的参数类型来推断出正确的类型
1 | //泛型推理机制调用泛型方法 |
泛型方法无法只根据返回值的类型推断出类型
1 | public static T GetValue<T>() |
1 | GetValue<int>(); |
泛型约束
T:struct
类型参数必须是值类型。可以指定除 Nullable 以外的任何值类型。
T:class
类型参数必须是引用类型,包括任何类、接口、委托或数组类型。
T:new()
类型参数必须具有无参数的公共构造函数。当与其他约束一起使用时,new() 约束必须最后指定。
T:<基类名>
类型参数必须是指定的基类或派生自指定的基类。
T:<接口名称>
类型参数必须是指定的接口或实现指定的接口。可以指定多个接口约束。约束接口也可以是泛型的。
T:U
为 T 提供的类型参数必须是为 U 提供的参数或派生自为 U 提供的参数。这称为裸类型约束。
泛型方法中泛型参数的约束
1 | public T GetTValue<T>(T t)where T:IList |
类型T必须是IList类型的
1 | GetTValue(new List<int>(){1212}) |
无法为类级别的泛型参数提供方法级别的约束
1 | public class MyClass<T> |
类实例化的时候,T类型已经确定,方法处无法再进行约束,正确的方法
1 | public class MyClass<T> where T:IComparable<T> |
泛型参数虚方法的重写:子类方法必须重新定义该方法特定的泛型参数
1 | public class MyBaseClass |
同时子类中的泛型方法不能重复基类泛型方法的约束
1 | public class MyBaseClass |
类中定义的委托可以使用该类的泛型参数
1 | public class MyClass<T> |
用作约束的泛型类型参数称为裸类型约束
1 | class List<T> |