C#泛型与C ++模板进行了比较

时间:2009-07-30 17:38:44

标签: c# c++ generics templates comparison

  

可能重复:
  What are the differences between Generics in C# and Java… and Templates in C++?

C#泛型与C ++模板之间有什么区别?我明白他们并没有解决完全相同的问题,那么两者的优点和缺点是什么?

5 个答案:

答案 0 :(得分:20)

您可以将C ++模板视为一种伪装成泛型系统的解释型函数式编程语言。如果这不会吓到你,它应该:)

C#泛型非常有限;您可以参数化一个或多个类型的类,并在方法中使用这些类型。因此,要从MSDN中获取示例,您可以执行以下操作:

public class Stack<T>
{
   T[] m_Items; 
   public void Push(T item)
   {...}
   public T Pop()
   {...}
}

现在你可以声明Stack<int>Stack<SomeObject>并且它会安全地存储该类型的对象(即,不担心错误地放入SomeOtherObject)。

在.NET内部,.NET运行时会将其专门化为基本类型(如int)的变体,以及对象类型的变体。例如,这允许Stack<byte>的表示远小于Stack<SomeObject>的表示。

C ++模板允许类似的用途:

template<typename T>
class Stack
{
    T *m_Items;
    public void Push(const T &item)
    {...}
    public T Pop()
    {...}
};

乍一看看起来很相似,但有一些重要的区别。首先,对于每个基本类型而不是一个变体,而不是每个基本类型都有一个变体,每个类型都有一个变体,它是针对实例化的。这可能是很多类型!

下一个主要区别是(在大多数C ++编译器上)它将在它使用的每个翻译单元中编译。这可能会减慢编译速度。

C ++模板的另一个有趣的属性是它们可以应用于除类之外的其他东西 - 当它们存在时,它们的参数可以被自动检测到。例如:

template<typename T>
T min(const T &a, const T &b) {
  return a > b ? b : a;
}

类型T将由使用该函数的上下文自动确定。

这些属性可以用来达到目的,牺牲你的理智。因为C ++模板是针对它所使用的每种类型重新编译的,并且编译器的实现始终可供编译器使用,所以C ++可以对模板进行非常积极的内联。除此之外,还可以自动检测函数中的模板值,并使用anonymous pseudo-functions在C ++中创建boost::lambda。因此,表达式如下:

_1 + _2 + _3

使用严重可怕的类型生成一个对象,该类型有一个运算符(),用于将其参数相加。

C ++模板系统还有很多其他的黑暗角落 - 它是一个非常强大的工具,但是可能很难思考,有时难以使用 - 特别是当它给你一个长达20页的错误消息时。 C#系统更简单 - 功能更强大,但更容易理解,更难滥用。

答案 1 :(得分:3)

http://blogs.msdn.com/csharpfaq/archive/2004/03/12/88913.aspx

粗略地说,大部分差异与模板在编译时解析,并且泛型在运行时得到解决这一事实有关。

答案 2 :(得分:2)

答案 3 :(得分:1)

这个blog entry from Eric Gunnerson很好地涵盖了这个主题。

最大的直接差异是模板是编译时功能,而泛型是运行时功能。

答案 4 :(得分:0)