15

在阅读了这个询问“特殊类”到底是什么的问题后,我留下了一个问题,为什么选择并硬编码这六个类、 、和作为System.Object特殊System.Array类,以防止它们被用作泛型类或方法的约束.System.DelegateSystem.EnumSystem.ValueType

很容易理解为什么System.Object会在那里;所有类都继承System.Object,因此无需将其包含为约束。我不清楚的是为什么其他人被选为这个特殊类别的一部分。

PS:当尝试将特殊类用作约束时,会引发编译错误 CS0702。

4

1 回答 1

7

在将泛型约束甚至泛型添加到 .NET 框架并将对它们的支持添加到 C# 语言之前,这些类已经不同。

它们每个的共同点是从它们继承与其他类型不同:

System.Object:在 C# 中你不能不继承这个。

System.Array您通过创建现有类型的数组(Array x = new int[2];等)来继承它

System.Delegatedelegate您通过创建一个(然后派生自MulticastDelegate,也是一个“特殊类型”,派生自)来继承它Delegate

System.Enum您通过创建一个enum.

System.ValueType您通过创建一个struct.

现在,请注意,除了new()通用约束之外,所有这些都与接口的继承或实现有关(在许多方面类似于继承)。事实上,其他限制是不能使用指针类型,也不能使用密封类型;无论如何您都不能拥有派生类型的两种情况(尽管禁止密封类型主要是因为您可能在不需要时创建泛型类型或方法,并且试图保护您免受自己的侵害) .

因此,当遇到有关继承的特殊情况时,基于继承特性(如约束)的代码可能不得不涉及特殊情况。这些特殊情况以最简单的方式处理:禁止它们。

在许多情况下,该值也较小:

System.Object由于唯一不能转换System.Object的类型是指针类型,而且无论如何这些都不能用作泛型参数,因此任何此类约束都是多余的。

System.Array您可以根据元素类型进行定义:void DoSomethingWithArray<T>(T[] array)等。

System.Delegate:这样会很有用,虽然在很多情况下我们可以根据参数和/或返回类型来定义,但有些情况下这并不能捕捉到。

System.Enum:会有用的。

System.ValueType:已经处理了;约束为struct。相反,我们也可以限制class排除这种情况,因此我们实际上有一个“不继承自……”选项,否则我们没有。

这并不是否认能够Delegate在减少了较少的限制。MulticastDelegateEnumEnum

于 2015-05-12T12:41:07.417 回答