编译器如何处理模板?

C++ How do compilers handle templates

本文关键字:处理 何处理 编译器      更新时间:2023-10-16

你们中的一些人可能从我最近的帖子中知道,我正在为c++考试学习,课程的内容非常糟糕。我基本上必须自学所有的东西,所以请原谅我在这里。

这是一个考试问题:

(i)解释c++语言中定义的模板概念。一定要区分程序员所做的和用户所做的编译器。

我现在的理由:

(i)模板允许函数或类使用泛型进行操作。这允许程序员一次有效地编写X功能,并且能够在许多不同的数据类型中使用该功能,而不必多次重写应用程序或部分应用程序。

我的问题是我不知道编译器如何处理模板的使用。

我不确定编译器在这个阶段做什么,如果有人能澄清这将是有帮助的

c++中的模板是通过替换实现的。它不像Java泛型,只是对涉及泛型类的代码进行类型检查,然后使用原始引用(类型擦除)进行编译。

基本上,c++为代码中使用的每个实际模板参数创建一个不同的类/方法。如果你有
template<typename T>
void myMethod(T t)
{
  //
}

在编译时发生的情况是,为模板实际使用的每种类型编译不同的方法。如果您在myMethod(50)myMethod("foo")上使用它,那么在运行时该方法的两个重载版本将可用。直观地说,这意味着模板可能会产生代码膨胀,但在实践中,没有可读性较差的模板,更大的代码库也能获得相同的表达性,所以这不是一个真正的问题。

所以它们背后没有黑魔法(如果你考虑元编程或部分专业化,就会有)。

假设你用模板写了一个函数:

template <typename T>
void function(T t){
 doSomething();
}

对于调用该函数的每种数据类型,编译器简单地用该数据类型替换'T',说'int',并为其生成代码,就像您从一开始就用'int'而不是'T'来编写这个函数一样。如果别人同意的话,这可能是正确的(但不是完整的)答案。

对于您创建的不同类型的对象的每个实例,或者对于您使用的不同类型的参数的函数,编译器只是在编译时生成一个重载版本。所以如果你有一个模板函数,比如排序函数,并且用这个函数来处理int和double数组,那么编译器实际上已经生成了两个函数:一个使用int,另一个使用double。这是我能给出的最简单的解释。希望对大家有用。