相关文章推荐
幸福的手术刀
·
韩国女主播韩宝贝合集
·
2 月前
·
聪明伶俐的单杠
·
长岛海洋生态文明综合试验区 意见征集 ...
·
1 年前
·
谦虚好学的钥匙
·
我的房客是妖怪漫画 - 抖音
·
1 年前
·
豪爽的篮球
·
史鉴丨古琴与陶渊明的风度_北京日报APP新闻
·
1 年前
·
谈吐大方的跑步鞋
·
如何评价谢苗主演的电影《东北警察故事 ...
·
1 年前
·
Code
›
04 | 编译阶段能做什么:属性和静态断言
静态方法
编译程序
linux编译
静态函数
https://time.geekbang.org/column/article/235295
慷慨的丝瓜
1 年前
罗剑锋的C++实战笔记
罗剑锋
奇虎360技术专家,Nginx/OpenResty开源项目贡献者
立即订阅
3732 人已学习
课程目录
已完结 30 讲
0/4
登录后,你可以任选
4
讲全文学习。
课前导读 (2讲)
开篇词 | 把C++从“神坛”上拉下来,这次咱这么学
免费
课前准备 | 搭建实验环境
概论 (5讲)
01 | 重新认识C++:生命周期和编程范式
02 | 编码阶段能做什么:秀出好的code style
03 | 预处理阶段能做什么:宏定义和条件编译
04 | 编译阶段能做什么:属性和静态断言
05 | 面向对象编程:怎样才能写出一个“好”的类?
语言特性 (5讲)
06 | auto/decltype:为什么要有自动类型推导?
07 | const/volatile/mutable:常量/变量究竟是怎么回事?
08 | smart_ptr:智能指针到底“智能”在哪里?
09 | exception:怎样才能用好异常?
10 | lambda:函数式编程带来了什么?
标准库 (4讲)
11 | 一枝独秀的字符串:C++也能处理文本?
12 | 三分天下的容器:恰当选择,事半功倍
13 | 五花八门的算法:不要再手写for循环了
14 | 十面埋伏的并发:多线程真的很难吗?
技能进阶 (4讲)
15 | 序列化:简单通用的数据交换格式有哪些?
16 | 网络通信:我不想写原生Socket
17 | 脚本语言:搭建高性能的混合系统
18 | 性能分析:找出程序的瓶颈
总结篇 (5讲)
19 | 设计模式(上):C++与设计模式有啥关系?
20 | 设计模式(下):C++是怎么应用设计模式的?
21 | 知识串讲(上):带你开发一个书店应用
22 | 知识串讲(下):带你开发一个书店应用
期末测试 | 这些C++核心知识,你都掌握了吗?
结束语 (1讲)
结束语 | 路远,未有穷期
轻松话题 (4讲)
轻松话题(一) | 4本值得一读再读的经典好书
轻松话题(二) | 给你分享我的工作百宝箱
轻松话题(三) | 提高生活质量的App
轻松话题(四) | 真正高效的生活,是张弛有度
罗剑锋的C++实战笔记
15
15
00:00/00:00
0.75x 1.25x
登录
|
注册
04 | 编译阶段能做什么:属性和静态断言
罗剑锋
2020-05-14
你好,我是 Chrono。
前面我讲了 C++ 程序生命周期里的“编码阶段”和“预处理阶段”,它们的工作主要还是“文本编辑”,生成的是
人类可识别的源码
(source code)。而“编译阶段”就不一样了,它的目标是
生成计算机可识别的机器码
(machine instruction code)。
今天,我就带你来看看在这个阶段能做些什么事情。
编译阶段编程
编译是预处理之后的阶段,它的输入是(经过预处理的)C++ 源码,输出是
二进制可执行文件
(也可能是汇编文件、动态库或者静态库)。这个处理动作就是由编译器来执行的。
和预处理阶段一样,在这里你也可以“面向编译器编程”,用一些指令或者关键字让编译器按照你的想法去做一些事情。只不过,这时你要面对的是庞大的 C++ 语法,而不是简单的文本替换,难度可以说是高了好几个数量级。
编译阶段的特殊性在于,它看到的都是 C++ 语法实体,比如 typedef、using、template、struct/class 这些关键字定义的类型,而不是运行阶段的变量。所以,这时的编程思维方式与平常大不相同。我们熟悉的是 CPU、内存、Socket,但要去理解编译器的运行机制、知道怎么把源码翻译成机器码,这可能就有点“强人所难”了。
</div></div></div></div> <div class="simplebar-placeholder" style="width: auto; height: 240px;"/></div> <div class="simplebar-track simplebar-horizontal" style="visibility: hidden;"><div class="simplebar-scrollbar simplebar-visible" style="width: 0px; display: none;"/></div> <div class="simplebar-track simplebar-vertical" style="visibility: visible;"><div class="simplebar-scrollbar simplebar-visible" style="; display: none;"/></div></div> <div class="_2XxzQqjL_0" style="display: none;"><div class="_1KDQg3Bq_0">确认放弃笔记?</div> <div class="mJWK5em0_0">放弃后所记笔记将不保留。</div></div> <div class="_3tbfXQau_0" style="display: none;"/></div> <div class="_1Ax_ZpPk_0"><div class="_2OgrMv3n_0">取消</div> <div class="FKyaWb-t_0">完成</div> <!----> <!----> <!----></div> <div class="_3MpaRWpt_0"><span>0/1000字</span></div></div> <div class="zbKHG1ec_0"><div class="tXxk8mk7_0">划线</div> <div class="_2YBWosuL_0"/> <div class="_25lruFgJ_0"/> <div class="_3wLabARi_0"/> <div class="tXxk8mk7_0">笔记</div> <div class="_2YBWosuL_0"/> <div class="tXxk8mk7_0">复制</div></div></div> <!----> <div class="_2sg1Tei__0"><span>©</span> 版权归极客邦科技所有,未经许可不得传播售卖。 页面已增加防盗追踪,如有侵权极客邦将依法追究其法律责任。 </div> <div class="_3qftfzyH_0"><div class="_2rnRKKqV_0">该试读文章来自付费专栏《罗剑锋的C++实战笔记》,如需阅读全部文章,<br/>请订阅文章所属专栏。</div> <div class="CJJSHwZ8_0">立即订阅</div></div></div> <div class="_2Vlfl3UO_0"><div class="_3SZaEKao_0"><img src="data:image/jpeg;base64,/9j/4QAYRXhpZgAASUkqAAgAAAAAAAAAAAAAAP/sABFEdWNreQABAAQAAABkAAD/4QN5aHR0cDovL25zLmFkb2JlLmNvbS94YXAvMS4wLwA8P3hwYWNrZXQgYmVnaW49Iu+7vyIgaWQ9Ilc1TTBNcENlaGlIenJlU3pOVGN6a2M5ZCI/PiA8eDp4bXBtZXRhIHhtbG5zOng9ImFkb2JlOm5zOm1ldGEvIiB4OnhtcHRrPSJBZG9iZSBYTVAgQ29yZSA1LjYtYzE0MCA3OS4xNjA0NTEsIDIwMTcvMDUvMDYtMDE6MDg6MjEgICAgICAgICI+IDxyZGY6UkRGIHhtbG5zOnJkZj0iaHR0cDovL3d3dy53My5vcmcvMTk5OS8wMi8yMi1yZGYtc3ludGF4LW5zIyI+IDxyZGY6RGVzY3JpcHRpb24gcmRmOmFib3V0PSIiIHhtbG5zOnhtcE1NPSJodHRwOi8vbnMuYWRvYmUuY29tL3hhcC8xLjAvbW0vIiB4bWxuczpzdFJlZj0iaHR0cDovL25zLmFkb2JlLmNvbS94YXAvMS4wL3NUeXBlL1Jlc291cmNlUmVmIyIgeG1sbnM6eG1wPSJodHRwOi8vbnMuYWRvYmUuY29tL3hhcC8xLjAvIiB4bXBNTTpPcmlnaW5hbERvY3VtZW50SUQ9InhtcC5kaWQ6YWE3YmZhMDItMzBhMC00MDg3LTg3MmYtOGMwMjMxNjNhZWRjIiB4bXBNTTpEb2N1bWVudElEPSJ4bXAuZGlkOjI2MTlEODM3NTgzMTExRTk5NDY4Qjk3QUFCNDFBN0QzIiB4bXBNTTpJbnN0YW5jZUlEPSJ4bXAuaWlkOjI2MTlEODM2NTgzMTExRTk5NDY4Qjk3QUFCNDFBN0QzIiB4bXA6Q3JlYXRvclRvb2w9IkFkb2JlIFBob3Rvc2hvcCBDQyAyMDE1IChNYWNpbnRvc2gpIj4gPHhtcE1NOkRlcml2ZWRGcm9tIHN0UmVmOmluc3RhbmNlSUQ9InhtcC5paWQ6OTYyRTNCMDNBREI4MTFFOEFFNTJDODlGREQ1OTUzMDMiIHN0UmVmOmRvY3VtZW50SUQ9InhtcC5kaWQ6OTYyRTNCMDRBREI4MTFFOEFFNTJDODlGREQ1OTUzMDMiLz4gPC9yZGY6RGVzY3JpcHRpb24+IDwvcmRm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" class="_1162B7i7_0"/> <div class="_20XltAts_0"><span class="ieiqepdd_0">登录</span> <span class="_2xgUAzrs_0">后留言</span></div></div> <div class="_1tbWAlsU_0 _23Q5Ko9I_0"><textarea placeholder="由作者筛选后的优质留言将会公开显示,欢迎踊跃留言。" rows="16" readonly="readonly" class="_2KHEOPSr_0"/></div> <!----></div> <div class="_3-W_zrq4_0"><h2>精选留言(23)</h2> <ul><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/15/9c/46/a2c1a99f.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>yelin</span> <!----></div> <div class="_2_QraFYR_0">斐布那契还可以这么玩,期待老师后面对于模版类的课程,我可能从来没都没学会过</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: 模板元编程比较复杂,属于屠龙之术,这次我先不讲,如果感兴趣的同学多可以以后单独开一个课程。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-14</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span>2</span></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class="">10</span></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/12/63/30/6f4b925c.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>Luca</span> <!----></div> <div class="_2_QraFYR_0">1. 因为属性标签都在编译器里内置,自定义的属性标签编译器无法识别。<br/>2. 静态断言可以作为编译期的一种约定,配合错误提示能够更快发现编译期的错误。</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: very nice。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-14</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span/></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class="">9</span></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/14/b4/63/84960032.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>lckfa李钊</span> <!----></div> <div class="_2_QraFYR_0">看到老师的斐波那契数列实现,我还是挺惊讶的,代码虽都看得懂,但是从没想过这么写,我有两个问题想请教下: 1.按本节的主题,编译阶段能做什么,所以说后面的那几个斐波那契数列在编译器就有结果了吗?如果是这样的话,肯定是需要cpu压栈计算的,这和真实的运行期有哪些不同呢?2.模板编程在哪些场景下使用比较好?模板编程 和 编译 阶段 似乎关联更大些</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: <br/>1.是的,这些代码都是模板类,自然会由编译器去解析处理,最后出来的也是编译期数值,也就是静态常量,省去了运行期的技术成本,运行期直接用就行。<br/><br/>2.模板元编程和预处理编程有点像,由编译器来改变源码的形态,但它的规则更复杂,难以理解,你首先要了解泛型编程,之后才能尝试模板元编程。<br/>对于80%的C++程序员来说,我不建议尝试模板元编程,可以参考第1讲。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-14</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span/></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class="">3</span></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/1c/f4/e4/e7471344.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>jxon-H</span> <!----></div> <div class="_2_QraFYR_0">第三次学习这节课的内容,感觉自己总算明白了罗老师的苦心。<br/>与一般的C++课不同,罗老师完全不讲语法要素这些百度一大把,而是从工作的原理和本质去剖析C++。<br/>我记得开课的第一讲,罗老师就这么说过,当时没啥体会,现在越发觉得这样的编排确实很高级。<br/>虽然对于我这种没怎么用过C++的人来说,接受所有信息有点吃力,但反而使我开阔视野,学习C++的时候,不会被限制语法语义的规则上,你还可以和预处理器、编译器打交道,让你的代码更好的让人和机器读懂。<br/>什么场景应该和预处理器沟通一下,什么时候和编译器沟通一下,这些都是高级的编程技巧。这些沟通也许是非必要的,但是掌握这些沟通技巧,在编程的时候将如鱼得水。<br/>对C++的钻研还不够深,功力不够,没发对老师的思考题发表有营养的见解,就这么表达一下自己的感受吧。</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: 有点过誉了,受之有愧。<br/><br/>因为C++比较复杂,所以我划出了四个生命周期,方便特性的归类和理解,不然混在一起很容易把思路弄乱。<br/><br/>C++需要在实践中学,要花的时间和精力还是挺多的,不过乐趣也自在其中。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-20</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span/></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class="">2</span></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/1e/74/ec/973fb3b7.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>逸清</span> <!----></div> <div class="_2_QraFYR_0">老师,自己C++基础知识还算了解,但代码写的太少,拿到一个需求无从下手,老师有没有比较好的方法或者适合练手的项目推荐?</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: 建议先学习一下标准库,了解里面的那些工具,现在开发很少有白手起家的了,用好工具,知道它们能解决哪些问题,写应用也就比较容易了。<br/><br/>比如string/regex处理字符串、map/set集合、线程库等等,跟着课程逐步学吧。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-14</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span/></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class="">2</span></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/16/f3/ea/2b2adda5.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>EncodedStar</span> <!----></div> <div class="_2_QraFYR_0">老师可以在每讲开始讲讲上一讲提到的问题吗?很多疑惑~<br/>用“静态断言”,是不是在代码严格要求是32位系统或者64位系统的时候也比较有用呢?32位系统和64位系统本身有的类型所占字节数不同。</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: <br/>1.课程都是预先录好的,所以不能及时回答,有问题写在留言里,我可以回复,还是希望自己思考得到答案。<br/><br/>2.静态断言的用处很多,判断32/64只是个最简单的例子,只要能够在编译阶段计算出的结果就可以断言,不过这就需要对编译阶段有比较多的认识了。<br/>不用着急,慢慢学C++,了解了泛型后再看静态断言可能就会好懂一些。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-19</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span/></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class="">1</span></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/16/f3/ea/2b2adda5.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>EncodedStar</span> <!----></div> <div class="_2_QraFYR_0">预处理可以自定义是直接将定义好的内容写到源码里,而标签不能自定义是因为编译器需要识别标签名</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: good</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-18</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span>1</span></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class="">1</span></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/1c/f6/5b/8e321b62.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>Carlos</span> <!----></div> <div class="_2_QraFYR_0">不得不说这节课让我回忆起了自己刚学会 vim macros 的感觉: 原来是我的想象力限制了 vim... 现在我想说: 原来是我的想象力限制了 c++...🧠<br/><br/>今天两个问题我都不是很懂, 希望老师指正. <br/><br/>1. 预处理阶段就是简单的文字替换, 编译阶段的属性标签应该需要编译器对这个标签进行 "一系列" 的配合, 过于复杂, 自己写容易翻车.<br/>2. 要写简洁易懂的备注, 告诉别人为什么我要在这里终止编译对你进行提醒. </div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: <br/>1.回答沾点边。实际上是因为属性标签必须要由编译器解释,而自定义标签编译器是不认识的,所以只能等编译器开发者去加,而不能是自己加。<br/><br/>2.说的比较好。<br/>静态断言是一种对编译环境的“前提”“假设”,要求在编译阶段必须如何如何,可以结合第1讲的生命周期,考虑一下应该如何发挥它的作用。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-14</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span/></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class="">1</span></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/12/52/24/bd63c4de.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>Eason Tai</span> <!----></div> <div class="_2_QraFYR_0">有一个问题:<br/>比如,在 libc-headers/fcntl.h 定义了 open,那么看到open函数是如何实现的呢?<br/>```cpp<br/>/* Open FILE and return a new file descriptor for it, or -1 on error.<br/> OFLAG determines the type of access used. If O_CREAT or O_TMPFILE is set<br/> in OFLAG, the third argument is taken as a `mode_t', the mode of the<br/> created file.<br/><br/> This function is a cancellation point and therefore not marked with<br/> __THROW. */<br/>#ifndef __USE_FILE_OFFSET64<br/>extern int open (const char *__file, int __oflag, ...) __nonnull ((1));<br/>#else<br/># ifdef __REDIRECT<br/>extern int __REDIRECT (open, (const char *__file, int __oflag, ...), open64)<br/> __nonnull ((1));<br/># else<br/># define open open64<br/># endif<br/>#endif<br/>#ifdef __USE_LARGEFILE64<br/>extern int open64 (const char *__file, int __oflag, ...) __nonnull ((1));<br/>#endif<br/>```<br/><br/></div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: 混合了宏定义和条件编译,实在是难以看懂。<br/><br/>可以直接gdb,看open到底是什么。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-06-01</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span/></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class=""/></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/1e/97/f9/3fcc851c.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>~灯火阑珊</span> <!----></div> <div class="_2_QraFYR_0">1.之前碰过一道面试题问:C++ assert的断言是怎么实现的? 如何编写跨平台的断言函数?. 我当时答的调用abort,感觉不好。这里不是可以从静态断言和动态断言两个方面答啊。老师对于这到面试题可不可以给点思路?<br/> <br/>2.文中"static_assert 可以在编译阶段定义各种前置条件,充分利用 C++ 静态类型语言的优势", 这句没理解可以举个例子么? 可以定义哪些前置条件啊? 《C++ 是静态类型语言》这个怎么理解呢?</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: <br/>1.这面试题太细节了,我也没有深究过,觉得这个题没什么意义。你的思路我觉得靠谱,可以展开来说。<br/><br/>2.在编译期断言各种条件,比如必须是64位平台,类型必须是指针,类型必须有某个成员函数,类型必须可以拷贝等等,需要有编译期的思维方式。<br/><br/>3.是相当于动态语言而言的,比如Python、php,变量类型是动态的。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-17</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span/></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class=""/></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/0f/8b/19/a15d060d.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>silverhawk</span> <!----></div> <div class="_2_QraFYR_0">属性这个,比起Java,python差好多,有了属性可以编译器静态的检查很多OO编程,比如override之类的对不对啊</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: 目前的C++11这块的确很弱,没办法,标准委员会效率就是低,不像公司那样无阻力大干快上。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-17</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span/></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class=""/></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/10/32/8d/a78327f7.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>幻境之桥</span> <!----></div> <div class="_2_QraFYR_0">1 预处理阶段的宏是我们自己来处理的,标签是编译器来处理,除非开发拓展编译器才需要或可以定义标签<br/>2 static_assert 可以在编译时检查是否满足编译环境要求,不满足直接编译失败,static_const 也类似吧!<br/><br/></div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: 说的很好。<br/><br/>不过后面的static_const不知道是什么,没这个关键字。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-17</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span>2</span></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class=""/></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="http://thirdwx.qlogo.cn/mmopen/vi_32/Q0j4TwGTfTIicr82CnrdEjibibAvyeKRQHszSzIAqoCWxN0kqC442XcjEae6S9j6NDtKLpg4Da4CUQQeUFUicWqiaDw/132" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>有学识的兔子</span> <!----></div> <div class="_2_QraFYR_0">1. 预处理不受编译器控制,由预处理器负责,给予宏的自由度比较大;而属性标签是为了简化编译器工作,而非为了扩展;<br/>2. 例如在编译阶段检查x64还得x86,跟常量运算有关的逻辑判断。</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: <br/>1.预处理器不需要理解宏,只是文本替换,而编译器必须要理解属性才能处理,自定义属性标签相当于是“外来语”,识别不了编译器就无法工作。<br/><br/>2.这个只是最基本的用法,随着对C++理解的深入,还可以对类型做各种静态检查。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-16</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span/></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class=""/></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/1d/99/2d/9b724aef.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>李学文 Alvin</span> <!----></div> <div class="_2_QraFYR_0">希望老师推荐一款Ubuntu16.4下C++编辑器或IDE,谢谢🙏</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: 我常用的就是vim,你可能不太习惯,其他的没用过,抱歉。<br/><br/>可以参考其他同学,用vs code,然后用插件远程登录Linux。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-15</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span>1</span></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class=""/></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/16/bc/25/1c92a90c.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>tt</span> <!----></div> <div class="_2_QraFYR_0">受语言的限制,编译阶段编程就只能“魔改”那些传统的语法要素了:把类当成函数,把模板参数当成函数参数,把“::”当成 return 返回值。<br/><br/>这个说法真形象,那些乱七八糟的语法一下就不面目可憎了。</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: 嗯,这也是我反复思考才得出的经验。<br/></p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-15</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span/></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class=""/></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/11/63/bd/80f587ad.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>丿淡忘</span> <!----></div> <div class="_2_QraFYR_0">在vs中使用 标记 deprecated 的方法 好像会报错<br/>c4996<br/>加上 宏可以解除报错 但也没有警告<br/>不知道老师有没有办法</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: 没用过vs,不好帮你。<br/><br/>不过我觉得上网搜一下,应该是个常见的问题,有解决方案。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-15</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span/></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class=""/></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/19/d6/67/5e0cac1b.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>Tedeer</span> <!----></div> <div class="_2_QraFYR_0">老师,因为在做Android时,会做一些java层的反编译;很少做so库的反编译,我很好奇so反编译生成的代码还会有这些属性标签和断言吗?</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: Android和Java不太熟,不是很了解。但我觉得,属性和断言都是源码级别的,如果反编译这些信息应该是看不见的。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-14</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span/></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class=""/></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/11/82/3d/356fc3d6.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>忆水寒</span> <!----></div> <div class="_2_QraFYR_0">学习了不少知识,期待老师能多讲讲C++ 一些在项目实战中 比较好用的方法。</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: 后面还有很多我在实际中的经验总结,可以慢慢看,有什么地方没讲到的也可以提,知无不言言无不尽。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-14</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span/></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class=""/></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="http://thirdwx.qlogo.cn/mmopen/vi_32/DYAIOgq83eqOpANMwDibLmj5IGJh6dTw300sZ1BHM5sG3sZv1A1rvCHOiblPD3jgFOiaMVVujtctWnQbVFoNPpRgw/132" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>alioo</span> <!----></div> <div class="_2_QraFYR_0">老师好,我看前面的回答是说template是在编译阶段完成的,但是我使用g++ compile.cpp -E发现并没有像上一节的宏,宏直接就计算出值了,然而template却没有计算</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: 注意,-E处理的是预处理阶段的宏,而template是编译阶段,这是两个完全不同的阶段。<br/><br/>编译阶段出来的结果直接就是二进制码了,是看不到源码的。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-14</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span>2</span></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class=""/></div></div></div></div></div> <!----></li><li><div class="_2sjJGcOH_0"><img src="https://static001.geekbang.org/account/avatar/00/10/5f/e5/54325854.jpg" class="_3FLYR4bF_0"/> <div class="_36ChpWj4_0"><div class="_2zFoi7sd_0"><span>范闲</span> <!----></div> <div class="_2_QraFYR_0">1.标签内置在编译器内部,无法进行自定义。<br/>2.断言在编译期间配合错误检查,能提前发现代码漏洞。</div> <div class="_10o3OAxT_0"><p class="_3KxQPN3V_0">作者回复: great。</p></div> <div class="_3klNVc4Z_0"><div class="_3Hkula0k_0">2020-05-14</div> <div class="_3_7joXrw_0"><!----> <div class="_3r0uuaYZ_0"><i class="iconfont"></i> <span/></div> <div class="_24fTab90_0"><i class="iconfont"></i> <span class=""/></div></div></div></div></div> <!----></li></ul> <div class="_1DRwKyCv_0"> 收起评论<span class="iconfont _1QBZRYBq_0"></span></div></div></div></div></div></div></div> <div class="simplebar-placeholder" style="width: auto; height: 9440px;"/></div> <div class="simplebar-track simplebar-horizontal" style="visibility: hidden;"><div class="simplebar-scrollbar simplebar-visible" style="width: 0px; display: none;"/></div> <div class="simplebar-track simplebar-vertical" style="visibility: visible;"><div class="simplebar-scrollbar simplebar-visible" style="height: 92px; display: block; transform: translate3d(0px, 0px, 0px);"/></div></div></div> <div class="_35V_pofE_0"><div class="_19KVU7IX_0 iconfont OJ1-O2lA_0 _3zAMGadh_0"><span>23</span></div> <div class="_3QWdWikl_0 iconfont OJ1-O2lA_0 _3zAMGadh_0"><!----></div> <div class="P00Ux77Z_0 iconfont OJ1-O2lA_0 _3zAMGadh_0"></div> <div class="_1GGnOK0Z_0 iconfont OJ1-O2lA_0 _3zAMGadh_0"></div> <div class="_23jDaBCo_0 iconfont OJ1-O2lA_0 _3zAMGadh_0"></div> <!----> <!----> <div class="FSrxdnjI_0 iconfont OJ1-O2lA_0 _3zAMGadh_0"><a href="//time.geekbang.org/download" target="_blank"><span class="_2NDI-Prg_0"></span><span class="_15yXCNVi_0">下载<br/>客户端</span></a></div> <div class="_2nVCVrRU_0 iconfont OJ1-O2lA_0 _3zAMGadh_0"><span class="_2NDI-Prg_0"></span><span class="_15yXCNVi_0">返回<br/>顶部</span></div></div> <div class="k7LpsVQS_0"><!----></div> <!----></div></div> <div class="_2sRsF5RP_0"/></div>
推荐文章
幸福的手术刀
·
韩国女主播韩宝贝合集
2 月前
聪明伶俐的单杠
·
长岛海洋生态文明综合试验区 意见征集 【意见征集】征求《关于深化全区应急管理综合行政执法改革的实施意见(征求意见稿)》意见的通知
1 年前
谦虚好学的钥匙
·
我的房客是妖怪漫画 - 抖音
1 年前
豪爽的篮球
·
史鉴丨古琴与陶渊明的风度_北京日报APP新闻
1 年前
谈吐大方的跑步鞋
·
如何评价谢苗主演的电影《东北警察故事 2》? - 知乎
1 年前