泛型是.NET 2.0引入的一个特性,它允许创建类、方法、类型等,而不需要指定具体的参数类型。这些参数必须在创建实例时提供。因此,可以将泛型视为一种蓝图或模板版本,实际的类型是在运行时定义的。
首先,来创建一个简单的泛型类,例如:
public class Point
{
// 类的实现
}
在这个例子中,创建了一个泛型类Point,它的坐标X和Y可以是任何类型。在本文中,将主要讨论泛型中的约束。
有时,可能需要一个泛型类,它只能接受特定类型的参数。例如,可能希望泛型类只能使用Point类型或其派生类型。这是否可能呢?答案是肯定的。C#提供了一种非常强大的方式实现这一特性。使用它,在某些时候定义泛型上的约束是非常有帮助的。
那么,如何定义泛型约束呢?这是通过使用where子句来实现的。在C#中,有两种类型的变量:引用类型和值类型。不,现在有三种类型:
将在另一篇文章中讨论可空类型。现在,让专注于泛型类型的约束。如果想要一个泛型类型,它可以被实例化为值类型,会怎么做?需要列出所有可能的值类型吗?不,知道,在C#中,类是引用类型,结构体是值类型。因此,可以定义一个泛型,它将只被实例化为值类型。例如,Point类可以是一个实时示例,它可以被实例化为值类型。这可以这样实现:
public class Point where T1 : struct
{
// 类的实现
}
同样,如果想要一个泛型,它只能是引用类型,那么它就是上面例子的相反。
public class Queue where T : class
{
// 类的实现
}
也可以有多个限制。可以使用逗号分隔的列表。那么,如何做到这一点呢?它可以是这样的:
public class Point where T1 : class
{
// 类的实现
}
但是,这意味着T是否遵循所有或任何一个。它应该遵循所有,就像这里T必须实现所有三个接口IEnumerable、IList和IDisposable。
在提供多个限制时,有一些限制。在多个限制中,只能包含一个类,但它可以有多个接口。此外,对类型的排序也有一些限制。类或结构体关键字应该首先出现,如果存在Class/Struct,它需要在All之前写。在这之后,任何类或基类,然后是所有其他接口。
也可以对泛型类型有多个限制,但它不能有冲突。例如,不能说:
public class Point where T : struct, class
{
// 类的实现
}
这将是一个编译时错误。
还可以有这样的约束:
public class Point where T : new()
{
// 类的实现
}
这里的意思是T必须是一个有无参构造函数的类型。可以有参数化的,但它也必须有无参的。它也可以与其他限制一起使用,但应该在列表的最后。
同样,可以对有多个参数的泛型类型应用约束。例如,下面的例子:
public class Point where T1 : class, new() where T2 : IList
{
// 类的实现
}
在这里,可以选择对它们中的任何一个或两个或一些应用约束。
认为这就是关于泛型约束的所有内容。可能想知道以下内容是否可能:
public class Point where T1 : int
{
// 类的实现
}
但这是不可能的。约束必须是一个接口,一个非密封类或一个类型。当编译时,会得到一个错误:“用作约束的类型必须是接口、非密封类或类型”。
希望都喜欢这篇文章。请分享反馈。