C#泛型是否支持类型签名约束?

时间:2011-07-01 20:16:31

标签: c# .net generics

C ++模板的一个好处是你(隐式地)可以要求某种类型的签名(例如,类型T需要一个不带参数的函数x并返回一个int)。 C#泛型是否支持类似的东西?

我知道基于基类或接口的约束,但这不是我想要的。

(作为一名学习C#的C ++程序员,我可能会误认为这是你在C#中想要的一个功能。任何对此的评论都会受到批评......)

7 个答案:

答案 0 :(得分:6)

除了你已经看到的限制之外什么都没有(公平地说,它涵盖了很多常见的场景)。有一些常见的解决方法:

  • dynamic,4.0
  • 使用反射或IL生成等手动鸭子打字

但这些都没有静态类型检查等。

答案 1 :(得分:4)

是的,通过界面。您可以定义具有必须实现特定接口的类型的通用对象。在该接口中,您实际上将强制添加到该泛型的任何对象(例如,列表)具有特定签名。

无论你是寻找的是什么,这就是你完成它的方式。 :)

答案 2 :(得分:3)

不,这是不可能的。这主要是由C ++模板和C#泛型之间的差异引起的:

编译C ++模板时,生成的代码类似vector<int>vector<string>。这意味着编译器必须知道所有可能的类型参数,但这也意味着它可以检查它们的正确性。

编译C#泛型类型时,实际上只创建了一种泛型类型:List<T>。因此,C#编译器不必知道编译类型的所有可能类型,这意味着您可以在二进制库中使用泛型类型,这在C ++中是不可能的。但这也意味着你无法检查所有类型。为了能够做这样的事情,有一些约束,但它们不能做C ++的编译时间检查可以做的几件事,比如检查某些方法的存在(不使用接口或某些基类)或是否存在合适的运算符。

在C#4中,您可以使用dynamic实现与此类模板类似的效果,但这样做 no 编译时检查,这意味着您将失去安全性 - 您可以放置在没有相应成员的类型中,在运行时到达该行代码之前,您将无法找到它。

答案 3 :(得分:1)

没有。这就是interface的用途。创建一个interface,在类型约束中定义要强制执行的合同。然后在约束中指定。

答案 4 :(得分:0)

在.Net中可以对泛型有5种类型的约束:

  1. 派生约束表明类型参数的优势。
  2. 接口约束是由type参数实现的接口。
  3. 值类型约束将类型参数限制为值类型。
  4. 引用类型约束将类型参数限制为引用类型。
  5. 构造函数约束规定type参数具有默认或无参数构造函数。
  6. This页面显示了更多信息。

答案 5 :(得分:0)

不,c#不支持。就像你说的,最接近的事情要求你让类实现一个通用的接口。

可以尝试通过签名来查找带有反射的行为,但这是运行时约束,而不是编译时约束。

答案 6 :(得分:0)

不,C#没有这样的约束。

如您所知,泛型约束只能强制继承基类或接口,或其他一些约束(构造函数约束new(),引用类型约束class,值类型约束{{1 }})。

您可以使用代理来实现所需的行为,并且有许多通用代表可用。
例如,struct是一个不带参数并返回Func<int>的委托。 int需要Func<string, DateTime, int>string并返回DateTime等等...