当前位置:首页 > 科技  > 软件

C++模板背后的黑箱操作:编译器

来源: 责编: 时间:2023-12-08 09:14:52 329观看
导读一、编译器如何处理模板1.模板代码的处理为了理解模板的复杂性,你需要了解编译器是如何处理模板代码的。当编译器遇到模板方法定义时,它会进行语法检查,但实际上不会编译模板。编译器不能编译模板定义,因为它不知道这些模

一、编译器如何处理模板

1.模板代码的处理

为了理解模板的复杂性,你需要了解编译器是如何处理模板代码的。当编译器遇到模板方法定义时,它会进行语法检查,但实际上不会编译模板。编译器不能编译模板定义,因为它不知道这些模板将用于哪些类型。编译器不可能为像 x = y 这样的代码生成代码,而不知道 x 和 y 的类型。pWU28资讯网——每日最新资讯28at.com

pWU28资讯网——每日最新资讯28at.com

当编译器遇到模板的实例化,例如 Grid<int>,它会通过将类模板定义中的每个 T 替换为 int 来为 int 版本的 Grid 模板编写代码。当编译器遇到模板的不同实例化,例如 Grid<SpreadsheetCell>,它会为 SpreadsheetCell 编写另一个版本的 Grid 类。编译器只是写出了如果没有模板支持,你需要为每种元素类型编写单独类时的代码。这里没有魔法;模板只是自动化了一个烦人的过程。如果你在程序中没有为任何类型实例化类模板,那么类方法定义就永远不会被编译。pWU28资讯网——每日最新资讯28at.com

这种实例化过程解释了为什么你需要在定义的各个地方使用 Grid<T> 语法。当编译器为特定类型(如 int)实例化模板时,它会将 T 替换为 int,使 Grid<int> 成为该类型。pWU28资讯网——每日最新资讯28at.com

2.选择性实例化

对于隐式类模板实例化,如以下示例:pWU28资讯网——每日最新资讯28at.com

Grid<int> myIntGrid;

编译器总是为类模板的所有虚拟方法生成代码。然而,对于非虚拟方法,编译器只为你实际调用的那些非虚拟方法生成代码。例如,给定前面的 Grid 类模板,假设你在 main() 中写了这样的代码(仅此代码):pWU28资讯网——每日最新资讯28at.com

Grid<int> myIntGrid;myIntGrid.at(0, 0) = 10;

编译器仅为 int 版本的 Grid 生成无参数构造函数、析构函数和非 const 的 at() 方法。它不会生成其他方法,如拷贝构造函数、赋值运算符或 getHeight()。这被称为选择性实例化。pWU28资讯网——每日最新资讯28at.com

存在的风险是,某些类模板方法中的编译错误可能会被忽略。未使用的类模板方法可能包含语法错误,因为这些不会被编译。这使得测试所有代码的语法错误变得困难。pWU28资讯网——每日最新资讯28at.com

你可以通过使用显式模板实例化来强制编译器为所有方法(虚拟和非虚拟)生成代码。以下是一个示例:pWU28资讯网——每日最新资讯28at.com

template class Grid<int>;

注意:显式模板实例化有助于发现错误,因为它强制编译器编译所有即使未使用的类模板方法。使用显式模板实例化时,不要只尝试使用基本类型(如 int)实例化类模板,还要尝试使用更复杂的类型(如 string)。pWU28资讯网——每日最新资讯28at.com

pWU28资讯网——每日最新资讯28at.com

二、模板对类型的要求

1.类型独立的代码编写

当你编写与类型无关的代码时,必须对这些类型做出某些假设。例如,在 Grid 类模板中,你假设元素类型(由 T 表示)是可销毁的、可拷贝/移动构造的,以及可拷贝/移动赋值的。pWU28资讯网——每日最新资讯28at.com

当编译器尝试用不支持类模板方法所使用的所有操作的类型来实例化模板时,代码将无法编译,且错误消息通常相当晦涩难懂。pWU28资讯网——每日最新资讯28at.com

然而,即使你想使用的类型不支持类模板的所有方法所需的操作,你也可以利用选择性实例化来使用某些方法而不是其他方法。pWU28资讯网——每日最新资讯28at.com

2.C++20 引入的概念(Concepts)

C++20 引入了概念(concepts),允许你为模板参数编写编译器可以解释和验证的要求。如果传递给模板实例化的模板参数不满足这些要求,编译器可以生成更易读的错误消息。后面将讨论概念。pWU28资讯网——每日最新资讯28at.com

概念为模板编程增加了额外的类型安全性,它通过为模板参数提供一个明确的接口合约来实现。这种方式不仅可以防止类型不匹配的问题,还可以改善模板错误消息的可读性,从而使模板代码更容易维护和理解。pWU28资讯网——每日最新资讯28at.com

pWU28资讯网——每日最新资讯28at.com

三、类模板代码的文件

在类模板中,类模板定义和方法定义必须对任何使用它们的源文件可用。有几种机制可以实现这一点:pWU28资讯网——每日最新资讯28at.com

1.方法定义与类模板定义在同一文件

你可以将方法定义直接放在定义类模板本身的模块接口文件中。当你在另一个源文件中导入这个模块以使用模板时,编译器将能够访问它所需的所有代码。这种机制用于之前的 Grid 实现。pWU28资讯网——每日最新资讯28at.com

2.方法定义在单独的文件

或者,你可以将类模板方法定义放在一个单独的模块接口分区文件中。然后,你还需要将类模板定义放在自己的分区中。例如,Grid 类模板的主模块接口文件可能如下所示:pWU28资讯网——每日最新资讯28at.com

export module grid;export import :definition;export import :implementation;

这导入并导出了两个模块分区:定义(definition)和实现(implementation)。类模板定义在定义分区中定义:pWU28资讯网——每日最新资讯28at.com

export module grid:definition;import <vector>;import <optional>;export template <typename T> class Grid { ... };

方法的实现位于实现分区中,该分区还需要导入定义分区,因为它需要 Grid 类模板定义:pWU28资讯网——每日最新资讯28at.com

export module grid:implementation;import :definition;import <vector>;...export template <typename T> Grid<T>::Grid(size_t width, size_t height)    : m_width { width }, m_height { height } { ... }

本文链接:http://www.28at.com/showinfo-26-39515-0.htmlC++模板背后的黑箱操作:编译器

声明:本网页内容旨在传播知识,若有侵权等问题请及时与本网联系,我们将在第一时间删除处理。邮件:2376512515@qq.com

上一篇: Python入门必备:细讲Python推导式

下一篇: 用 print 太慢了!强烈推荐这款 Python Debug 工具

标签:
  • 热门焦点
  • Find N3入网:最高支持16+1TB

    OPPO将于近期登场的Find N3折叠屏目前已经正式入网,型号为PHN110。本次Find N3在外观方面相比前两代有很大的变化,不再是小号的横向折叠屏,而是跟别的厂商一样采用了较为常见的
  • K60至尊版刚预热 一加Ace2 Pro正面硬刚

    Redmi这边刚如火如荼的宣传了K60 Ultra的各种技术和硬件配置,作为竞品的一加也坐不住了。一加中国区总裁李杰发布了两条微博,表示在自家的一加Ace2上早就已经采用了和PixelWo
  • Mate60手机壳曝光 致敬自己的经典设计

    8月3日消息,今天下午博主数码闲聊站带来了华为Mate60的第三方手机壳图,可以让我们在真机发布之前看看这款华为全新旗舰的大致轮廓。从曝光的图片看,Mate 60背后摄像头面积依然
  • 掘力计划第 20 期:Flutter 混合开发的混乱之治

    在掘力计划系列活动第20场,《Flutter 开发实战详解》作者,掘金优秀作者,Github GSY 系列目负责人恋猫的小郭分享了Flutter 混合开发的混乱之治。Flutter 基于自研的 Skia 引擎
  • 一年经验在二线城市面试后端的经验分享

    忠告这篇文章只适合2年内工作经验、甚至没有工作经验的朋友阅读。如果你是2年以上工作经验,请果断划走,对你没啥帮助~主人公这篇文章内容来自 「升职加薪」星球星友 的投稿,坐
  • 每天一道面试题-CPU伪共享

    前言:了不起:又到了每天一到面试题的时候了!学弟,最近学习的怎么样啊 了不起学弟:最近学习的还不错,每天都在学习,每天都在进步! 了不起:那你最近学习的什么呢? 了不起学弟:最近在学习C
  • 三星获批量产iPhone 15全系屏幕:苹果史上最惊艳直屏

    按照惯例,苹果将继续在今年9月举办一年一度的秋季新品发布会,有传言称发布会将于9月12日举行,届时全新的iPhone 15系列将正式与大家见面,不出意外的话
  • 半导体需求下滑 三星电子DS业务部门今年营业亏损预计超10万亿韩元

    7月17日消息,据外媒报道,去年下半年开始的半导体需求下滑,影响到了三星电子、SK海力士、英特尔等诸多厂商,营收明显下滑,部分厂商甚至出现了亏损。作为
  • 2299元起!iQOO Pad开启预售:性能最强天玑平板

    5月23日,iQOO如期举行了新品发布会,除了首发安卓最强旗舰处理器的iQOO Neo8系列新机外,还在发布会上推出了旗下首款平板电脑——iQOO Pad,其搭载了天玑
Top