C ++模块 - 为什么它们从C ++ 0x中删除?他们以后会回来吗?

时间:2010-08-29 19:03:46

标签: c++ c++11 module standards language-extension

我刚发现这个old C++0x draft关于C ++ 0x中的模块。

这个想法是通过只写.cpp文件退出当前的.h / .cpp系统,然后在编译过程中生成模块文件,然后由其他.cpp文件使用。

这看起来非常棒。

但我的问题是:他们为什么要把它从C ++ 0x中删除?是因为太多的技术难题?时间不够?你是否认为他们会考虑使用它来获得一个不可思议的C ++版本?

4 个答案:

答案 0 :(得分:89)

C ++模块草案(C ++ 17之后的技术规范)

WG21已在open-std.org上发布了关于C / C ++模块规范的草案和几个更新版本。我只会链接到这里的最新文件:

  • 工作草案,C ++模块扩展程序 N4610 (2016年10月)。
  • 第四次修订以 P0142R0 (2016年3月)发布。
  • 发布为 P0143R2 的模块的措辞(2016年3月)。
  • clang团队发布了他们更改的第二次修订: P0273R1 (2016年10月)。

以下博客文章包含标准会议的摘要,特别是模块草案的当前状态摘要:

更新:正如我在上面链接的Kona旅行报告中所述,目前有两个竞争提案,一个来自微软,一个来自Clang。 Microsoft提出的解决方案不允许导出宏,而Clang团队的解决方案将支持导出宏。到目前为止,只有Microsoft正式提交了模块规范草案。

Microsoft提出的模块规范

以下是此提案包含的最重要概念的快速概述。作为草案,这可能仍然会改变。新模块标准将包括以下内容:

用于声明模块的module关键字,多个文件可以声明这个以构建一个模块(但是对于每个模块,只有一个编译单元可以包含export {}部分):

module M;

要导入模块的import关键字,而不是import,可能还会决定使用using module,因此可以避免使用新的导入关键字。

import std.io;
import module.submodule;

export语法,定义作为此模块一部分的公共声明,非接口声明,不应作为其一部分导出模块将在导出块之外定义。 声明可以是C / C ++中的任何类型的声明,也就是说,不仅是函数,还包括变量,结构,模板,命名空间和类:

export {
    int f(int);
    double g(double, int);

    int foo;

    namespace Calc {
         int add(int a, int b);
    }        
}

void not_exported_function(char* foo);

模块的一个重要变化是宏和预处理器定义将是模块的本地定义,不会被导出。因此,宏对导入的模块没有任何影响:

#define FILE "my/file"
import std.io;   //will not be impacted by the above definition

重要的是,当前的预处理器系统和模块都能够共存,并且仍然可以使用标头来包含宏。

有关详细信息,我建议您阅读草稿。

Clang Modules

Clang一直致力于模块实施,可在the clang modules page找到。但是clang目前没有实现模块的具体语法,也就是说,Clang没有实现上述语法。为了解释这一点,该页面包含以下声明:

  

目前,导入声明没有C或C ++语法。 Clang将跟踪模块提案   在C ++委员会。请参阅包含为导入部分以了解模块今天如何导入。

Clang目前实施的主要部分是"模块地图语言"它允许为仍使用头文件的现有代码写入模块映射。

从模块中导出宏

如上所述,目前尚不清楚宏出口是否会成为最终模块TS 的一部分。在P0273R1中,为宏的导出提出了以下语法:

#export define MAX(A,B) ((A) > (B)) ? (A) : (B);

答案 1 :(得分:69)

State of C++ Evolution (Post San Francisco 2008)开始,模块提案被归类为“标题为单独的TR:”

  

这些主题被认为太重要了,无法在发布之前等待C ++ 0x之后的另一个标准,但是太过实验,无法及时完成下一个标准。因此,这些功能将尽早通过技术报告提供。

模块提案尚未就绪,等待它会延迟完成C ++ 0x标准。它并没有被真正删除,它从未被纳入工作文件中。

答案 2 :(得分:32)

Clang是第一个在标准化完成之前开始处理模块的编译器。目前还没有太多的文档,但可以在这里找到示例代码:
http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Modules/

道格拉斯格雷戈尔(开发商实施这些评论)的一些评论:
http://clang-developers.42468.n3.nabble.com/C-modules-td3619936.html

理论上,您可以定义一组辅助宏,如begin_module,end_module,import_module,以防止您将来可能发生的语法更改。

编辑1:
Douglas Gregor发布了关于他的实施的演讲:
http://llvm.org/devmtg/2012-11/Gregor-Modules.pdf?=submit

编辑2:
这里记录了clang中的模块支持:
http://clang.llvm.org/docs/Modules.html

编辑3:
现在,Microsoft的C ++编译器也支持模块: http://blogs.msdn.com/b/vcblog/archive/2015/12/03/c-modules-in-vs-2015-update-1.aspx

答案 3 :(得分:-40)

  1. 因为这是一个非常大的概念变化。
  2. 没有真正的需要,因为将源与h / cpp的分离完成了工作
  3. 因为C ++没有定义如何构建实际的“模块”库。它离开了 它是编译器开发人员和链接器。
  4. “模块”有时非常依赖于平台,例如DLL非常不同 来自共享对象。因此,在这些概念之间进行合并并非易事。