类型约束
基类约束有两个重要的目的。
1:它允许在泛型类中使用有约束指定的基类成员。
2:确保只能使用支持指定基类或派生类的类型实例。
约束是使用 where 上下文关键字指定的。
下表列出了五种类型的约束:
约束 | 说明 |
T:struct | 类型参数必须是值类型。可以指定除 Nullable 以外的任何值类型。 |
T:class | 类型参数必须是引用类型,包括任何类、接口、委托或数组类型。 |
T:new() | 类型参数必须具有无参数的公共构造函数。当与其他约束一起使用时,new() 约束必须最后指定。 |
T:<基类名> | 类型参数必须是指定的基类或派生自指定的基类。 |
T:<接口名称> | 类型参数必须是指定的接口或实现指定的接口。可以指定多个接口约束。约束接口也可以是泛型的。 |
T:U | 为 T 提供的类型参数必须是为 U 提供的参数或派生自为 U 提供的参数。这称为裸类型约束. |
1:派生约束:
将约束定义在父类中,由其派生出的子类将受其约束。
(1):被约束类进行约束,列表list可以使用约束类中的成员。类型为 T 的所有项都保证是 基类对象或从 基类继承的对象
(2):实例化list的时候,尖括号<>中类型只能是基类或是其派生类的数据类型来实例化。
实例:
class Program { static void Main(string[] args) { // 只能使用animal 或者dog (基类或者其派生类) 这就是约束 animalFamily<dog> cate = new animalFamily<dog>(); cate.Add(new dog("aaa")); cate.Add(new dog("bbb")); cate.Add(new dog("ccc")); cate.Display(); Console.ReadLine(); } } /// <summary> /// 动物基类 /// </summary> class animal { public string name; public animal(string nameValue) { name = nameValue; } } /// <summary> /// 狗类继承自动物类 /// </summary> class dog : animal { public dog(string nameValue) :base(nameValue) { } } /// <summary> /// 动物家庭类,继承自动物类 /// </summary> /// <typeparam name="T"></typeparam> class animalFamily<T> where T : animal { public List<T> family = new List<T>(); public void Add(T member) { family.Add(member); } public void Display() { foreach (T item in family) { Console.WriteLine(item.name); } } }
2:约束多个参数
可以对多个参数应用约束,并对一个参数应用多个约束,如下面的示例所示:
class Base { } class Test<T, U> where U : struct where T : Base, new() { }
关于约束,先简单看到这里,以后再补充。