首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >模板的编译是如何工作的?

模板的编译是如何工作的?
EN

Stack Overflow用户
提问于 2013-11-05 20:30:13
回答 7查看 27.3K关注 0票数 27

我正在读一本关于模板是如何工作的书,我很难理解这个模板的解释。

上面写着

当编译器看到模板的定义时,它不会生成代码。只有当我们实例化模板的特定实例时,它才会生成代码。代码只有在使用模板(而不是在定义它时)才会生成,这一事实影响了我们如何组织源代码,当错误为detected...To生成实例化时,编译器需要有定义函数模板或类模板成员函数的代码。因此,与非模板代码不同,模板的头通常包括定义和声明.

“生成代码”到底是什么意思?我不明白在编译函数模板或类模板时与常规函数或类有什么不同。

EN

回答 7

Stack Overflow用户

回答已采纳

发布于 2013-11-05 20:34:48

编译器为模板类实例化中给定的特定类型生成代码。

如果您有一个模板类声明,例如

代码语言:javascript
复制
template<typename T>
class Foo
{
public:
     T& bar()
     {
         return subject; 
     }
private:
     T subject;
};

例如,您就有了以下实例化

代码语言:javascript
复制
Foo<int> fooInt;
Foo<double> fooDouble;

这些将有效地生成--与您所定义的类相同的链接代码,如

代码语言:javascript
复制
class FooInt
{
public:
     int& bar()
     {
         return subject; 
     }
private:
     int subject;
}

代码语言:javascript
复制
class FooDouble
{
public:
     double& bar()
     {
         return subject; 
     }
private:
     double subject;
}

实例化如下所示的变量

代码语言:javascript
复制
FooInt fooInt;
FooDouble fooDouble;

关于模板definitions (无论是什么模板都不要与declarations混淆)需要与头(包括)文件一起查看的观点,很清楚为什么:

编译器不能在没有看到definition的情况下生成这段代码。不过,它可以引用在链接阶段首先出现的匹配实例化。

非模板成员函数有哪些允许在模板函数不具有的标头之外定义它?

非模板类/成员/函数的声明为链接器提供了一个预定义的入口点。定义可以从编译后的对象文件(== .cpp == compilation unit)中看到的单个实现中提取。

相反,模板化类/成员/函数的声明可以通过给定相同或变化的模板参数的任意编译单元实例化。这些模板参数的定义至少需要查看一次。它可以是通用的,也可以是专门的。

请注意,您可以对特定类型的模板实现进行专门化(包括在标头中或在特定的compilation unit中)。如果要在其中一个compilation units中为模板类提供专门化,并且不将模板类与专门化以外的类型一起使用,那么这也足以将其链接到一起。

我希望这个示例有助于澄清编译器的不同之处和努力之处。

票数 26
EN

Stack Overflow用户

发布于 2013-11-05 20:50:12

模板是用于创建代码的模式。当编译器看到模板的定义时,它会记录下该模式。当它看到一个使用该模板的时,它会挖掘它的注释,找出如何在使用它的地方应用该模式,并根据该模式生成代码。

票数 19
EN

Stack Overflow用户

发布于 2013-11-05 20:43:01

编译器在看到模板时应该做什么?为所有可能的数据类型生成所有的机器代码可能要花很多时间。或者只是有点懒惰,为它所需要的生成机器代码。

我想后一种选择是更好的解决方案,并完成工作。

票数 5
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/19798325

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档