C++ 20 的模块对老式头文件的兼容性和提升(流口水 ing - V2EX
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
RainyCRH
V2EX    C++

C++ 20 的模块对老式头文件的兼容性和提升(流口水 ing

  •  
  •   RainyCRH 2019-08-12 14:56:44 +08:00 4605 次点击
    这是一个创建于 2316 天前的主题,其中的信息可能已经有所发展或是发生改变。

    唠叨

    根据标准,模块兼容老式头文件(必须的)……

    如果写下 import <some_header.h>; 或者 import "some_header.h"; 这样的 import 语句,那么针对同一个头文件来说,它们会作为同一隐式的独立模块来编译,并且是原子的。

    而,现在的预处理器中,#include <some_header.h> 或者 #include "some_header.h" 则是无视任何 C++ 语义,暴力把文件内容复制粘贴进源文件……(逃

    #include 方式

    // hello.cpp #include "some_header.h" #include <vector> int main() { std::vector<int> numbers = { 1, 2, 3, 4, 5 }; cao_dan::fuck(numbers); } 

    针对如上源文件,如果我修改了这里面的任何内容,都会导致头文件 <vector>some_header.h 的内容被暴力 #include 进 hello.cpp 然后重新编译一次。

    如果头文件的内容,是一堆模板元的话……这编译速度,你懂的……(逃

    import 方式

    // hello.cpp import "some_header.h"; import <vector>; int main() { std::vector<int> numbers = { 1, 2, 3, 4, 5 }; cao_dan::fuck(numbers); } 

    这种方式,很好地兼容了老式头文件。不同的是,它把同一个头文件当成一个模块单元来编译,并生成 BMI (标准中叫 Binary Module Interface,即二进制模块接口)文件,缓存起来。这样在后续编译中,如果没改变头文件 some_header.h<vector> 的内容的话,构建系统就会直接加载这些 BMI,并链接,而不用重新编译。( 666

    有宏控制的情况

    问题来了:如果老式头文件中有宏控制怎么 bang ?

    // lagacy.h #pragma once #ifdef SOME_OPTION_1 // ... #elif defined(SOME_OPTION_2) //... #endif 

    针对以上头文件,采用 import "legacy.h" 的方式无法导入宏,也就无法让用户设置生效。这种情况,大佬们也考虑到了。推荐的做法是用包装头文件实现。

    // lagacy_some_option_1.h #pragma once #define SOME_OPTION_1 #include <lagacy.h> 
    // lagacy_some_option_2.h #pragma once #define SOME_OPTION_2 #include <lagacy.h> 

    这样 lagacy_some_option_1.h 就是针对 SOME_OPTION_1 的设置, lagacy_some_option_2.h 就是针对 SOME_OPTION_2 的设置。

    使用如下:

    // main.cpp import "lagacy_some_option_1.h" // import "lagacy_some_option_2.h" // ... 

    废话

    针对这个 BMI 以及其派生出来的 C++ 生态系统技术报告,准备在 C++ 20 发布之前拟定。主要包括一些亟待统一的地方:

    • 模块 ABI
    • 基于模块编译的二进制库的发布和使用
    • 针对入门者的友好的模块化 Hello World
    • 构建系统(如 CMake、MSBuild 等等)
    • 编译器实现(如 MSVC、Clang、GCC 等)
    • 名称查找规则(比如一个模块 boost.asio 怎么对应到具体的 BMI 文件或源文件,这个规则是什么?)
    • 模块世界的包管理工具(急需!)

    Over- -

    7 条回复    2019-08-31 09:48:04 +08:00
    v2byy
        1
    v2byy  
       2019-08-12 16:35:06 +08:00
    这个跟 vs 中的 Precompiled header 有什么区别吗?
    augustheart
        2
    augustheart  
       2019-08-12 16:41:53 +08:00
    已经能用了?
    araraloren
        3
    araraloren  
       2019-08-12 16:59:36 +08:00
    @v2byy 区别就是 这个是标准,你那个再厉害是小三 。。
    jim9606
        4
    jim9606  
       2019-08-12 21:00:15 +08:00
    这玩意就是为了优化编译过程,msvc 的预编译头就是这么干的。
    ABI 兼容我觉得是没戏的,C++已经放弃对 ABI 的标准化了,估计未来只能靠 C+操作系统了(C 标准也没有统一 ABI,只是 OS 规范了这个)
    c0011
        5
    c0011  
       2019-08-13 09:26:35 +08:00
    以前头文件不是可以写宏控制头文件只编译一次吗??
    FrankHB
        6
    FrankHB  
       2019-08-31 09:43:20 +08:00
    “一堆模板元”是什么鬼。
    FrankHB
        7
    FrankHB  
       2019-08-31 09:48:04 +08:00
    其实这种情况还是脱裤子放屁。#include 的语义并没有禁止这样的实现,而<>是 implementation-defined。够折腾了。
    搞得现在那么复杂,无非是跟 export 有一腿而已。然而看看别家(ML-like)叫 module 的东西,这坨也就是玩具。
    关于     帮助文档     自助推广系统     博客     API     FAQ     Solana     3838 人在线   最高记录 6679       Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 25ms UTC 05:20 PVG 13:20 LAX 21:20 JFK 00:20
    Do have faith in what you're doing.
    ubao msn snddm index pchome yahoo rakuten mypaper meadowduck bidyahoo youbao zxmzxm asda bnvcg cvbfg dfscv mmhjk xxddc yybgb zznbn ccubao uaitu acv GXCV ET GDG YH FG BCVB FJFH CBRE CBC GDG ET54 WRWR RWER WREW WRWER RWER SDG EW SF DSFSF fbbs ubao fhd dfg ewr dg df ewwr ewwr et ruyut utut dfg fgd gdfgt etg dfgt dfgd ert4 gd fgg wr 235 wer3 we vsdf sdf gdf ert xcv sdf rwer hfd dfg cvb rwf afb dfh jgh bmn lgh rty gfds cxv xcv xcs vdas fdf fgd cv sdf tert sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf shasha9178 shasha9178 shasha9178 shasha9178 shasha9178 liflif2 liflif2 liflif2 liflif2 liflif2 liblib3 liblib3 liblib3 liblib3 liblib3 zhazha444 zhazha444 zhazha444 zhazha444 zhazha444 dende5 dende denden denden2 denden21 fenfen9 fenf619 fen619 fenfe9 fe619 sdf sdf sdf sdf sdf zhazh90 zhazh0 zhaa50 zha90 zh590 zho zhoz zhozh zhozho zhozho2 lislis lls95 lili95 lils5 liss9 sdf0ty987 sdft876 sdft9876 sdf09876 sd0t9876 sdf0ty98 sdf0976 sdf0ty986 sdf0ty96 sdf0t76 sdf0876 df0ty98 sf0t876 sd0ty76 sdy76 sdf76 sdf0t76 sdf0ty9 sdf0ty98 sdf0ty987 sdf0ty98 sdf6676 sdf876 sd876 sd876 sdf6 sdf6 sdf9876 sdf0t sdf06 sdf0ty9776 sdf0ty9776 sdf0ty76 sdf8876 sdf0t sd6 sdf06 s688876 sd688 sdf86