0

0

C++如何利用C++20 Modules解决困扰已久的头文件包含问题?(工程现代化)

裘德小鎮的故事

裘德小鎮的故事

发布时间:2026-03-11 18:31:54

|

939人浏览过

|

来源于php中文网

原创

c++20模块需严格区分接口单元(export module name;)和实现单元(module name;),import仅可见export内容,构建须适配编译器参数与cmake模块属性,否则退化为头文件模式。

c++如何利用c++20 modules解决困扰已久的头文件包含问题?(工程现代化)

模块声明和定义怎么写才不被编译器报错

模块不是把 #include 换成 import 就完事。C++20 要求模块接口单元(interface unit)必须以 module 关键字开头,且只能有一个模块声明;实现单元(implementation unit)用 module module_name; 声明归属,不能用 export module

  • 接口文件(如 math.mpp)必须写:export module math;,后面跟 export 的函数或类声明
  • 实现文件(如 math.cpp)写:module math;,不加 export,只提供定义
  • 不能在头文件里混用 export module#include —— 编译器会直接拒绝,报错类似 error: module declaration must be the first non-comment, non-whitespace token
  • MSVC 要求模块文件后缀为 .ixx 或显式用 /experimental:module /module:interface 控制;Clang 和 GCC 则更倾向 .mpp + -x c++-system-header 类参数,不统一

import 之后为什么还是找不到符号

导入模块 ≠ 自动可见所有内容。import 只让 export 过的声明进入当前作用域,没 export 的函数、类型、宏、静态变量全都不见。

  • 如果 math.mpp 里写了 int helper(); 但没加 export,哪怕它在 export module math; 下面,import math; 后也调不到 helper()
  • export 不能修饰局部变量或函数内定义的类型;也不能修饰 using 指令(如 using namespace std;),但可以修饰 using 声明(如 export using std::vector;
  • 模块内 #include <vector></vector> 是允许的,但不会自动导出 std::vector —— 必须显式 export using std::vector;export template class std::vector<int>;</int>

混合使用 #include 和 import 时链接失败或 ODR 违反

头文件和模块共存是过渡期常态,但危险点在于:同一个实体(比如 class Widget)若既从传统头文件中 #include 进来,又被某个模块 export 过,就可能触发 ODR(One Definition Rule)违规 —— 编译器未必立刻报错,但链接阶段可能符号重复,或运行时行为异常。

Q.AI视频生成工具
Q.AI视频生成工具

支持一分钟生成专业级短视频,多种生成方式,AI视频脚本,在线云编辑,画面自由替换,热门配音媲美真人音色,更多强大功能尽在QAI

下载
  • 避免对同一库做双路径暴露:比如一边用 #include <fmt></fmt>,一边又自己封装了 export module fmt_wrapper;export import <fmt></fmt>(GCC/Clang 目前不支持直接 import 标准头,MSVC 有实验性 import std;,但不可移植)
  • 第三方库未提供模块接口时,老实用 #include;想封装,就用模块“桥接”,但桥接模块里不要 export 头文件里的定义,只 export 你自己的薄包装层(例如 export inline std::string to_string_v2(int x) { return fmt::to_string(x); }
  • 模块编译产物(如 .pcm.ifc)和目标平台强绑定:MSVC 的 .ifc 不能给 Clang 用,GCC 的 .gcm 也不兼容 —— 混合构建系统(如 CMake + 多编译器)下,模块缓存要按 compiler-id 分开管理,否则静默失效

构建系统怎么实际跑起来(以 CMake 3.27+ 为例)

CMake 对模块的支持仍偏底层,没到“开箱即用”程度。关键不是写对语法,而是让生成的构建规则正确传递模块依赖与接口路径。

立即学习C++免费学习笔记(深入)”;

  • 模块接口文件需用 set_property(SOURCE math.mpp PROPERTY CXX_MODULE_INTERFACE TRUE) 显式标记,否则 CMake 当普通源文件处理
  • 必须手动指定模块映射路径:target_compile_options(mylib PRIVATE $<join:>,=></join:>),不然 import 找不到模块名对应物理文件
  • 模块间依赖要用 target_link_libraries(other_module INTERFACE mylib),而不是 target_include_directories —— 后者对模块无效
  • 调试时发现模块没生效?检查 compile_commands.json 里是否出现了 -fmodules-ts(Clang)、/experimental:module(MSVC)或 -fmodules(GCC),缺一个就退回头文件模式
模块真正落地的卡点不在语法,而在构建链路的每一步都得同步适配:编译器参数、模块缓存位置、跨模块符号可见性控制、以及和既有头文件生态的隔离边界。稍有松动,就会退化成“写了模块语法,却仍被头文件污染”的状态。

热门AI工具

更多
DeepSeek
DeepSeek

幻方量化公司旗下的开源大模型平台

豆包大模型
豆包大模型

字节跳动自主研发的一系列大型语言模型

通义千问
通义千问

阿里巴巴推出的全能AI助手

腾讯元宝
腾讯元宝

腾讯混元平台推出的AI助手

文心一言
文心一言

文心一言是百度开发的AI聊天机器人,通过对话可以生成各种形式的内容。

讯飞写作
讯飞写作

基于讯飞星火大模型的AI写作工具,可以快速生成新闻稿件、品宣文案、工作总结、心得体会等各种文文稿

即梦AI
即梦AI

一站式AI创作平台,免费AI图片和视频生成。

ChatGPT
ChatGPT

最最强大的AI聊天机器人程序,ChatGPT不单是聊天机器人,还能进行撰写邮件、视频脚本、文案、翻译、代码等任务。

相关专题

更多
json数据格式
json数据格式

JSON是一种轻量级的数据交换格式。本专题为大家带来json数据格式相关文章,帮助大家解决问题。

455

2023.08.07

json是什么
json是什么

JSON是一种轻量级的数据交换格式,具有简洁、易读、跨平台和语言的特点,JSON数据是通过键值对的方式进行组织,其中键是字符串,值可以是字符串、数值、布尔值、数组、对象或者null,在Web开发、数据交换和配置文件等方面得到广泛应用。本专题为大家提供json相关的文章、下载、课程内容,供大家免费下载体验。

546

2023.08.23

jquery怎么操作json
jquery怎么操作json

操作的方法有:1、“$.parseJSON(jsonString)”2、“$.getJSON(url, data, success)”;3、“$.each(obj, callback)”;4、“$.ajax()”。更多jquery怎么操作json的详细内容,可以访问本专题下面的文章。

334

2023.10.13

go语言处理json数据方法
go语言处理json数据方法

本专题整合了go语言中处理json数据方法,阅读专题下面的文章了解更多详细内容。

82

2025.09.10

string转int
string转int

在编程中,我们经常会遇到需要将字符串(str)转换为整数(int)的情况。这可能是因为我们需要对字符串进行数值计算,或者需要将用户输入的字符串转换为整数进行处理。php中文网给大家带来了相关的教程以及文章,欢迎大家前来学习阅读。

1010

2023.08.02

scripterror怎么解决
scripterror怎么解决

scripterror的解决办法有检查语法、文件路径、检查网络连接、浏览器兼容性、使用try-catch语句、使用开发者工具进行调试、更新浏览器和JavaScript库或寻求专业帮助等。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

492

2023.10.18

500error怎么解决
500error怎么解决

500error的解决办法有检查服务器日志、检查代码、检查服务器配置、更新软件版本、重新启动服务、调试代码和寻求帮助等。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

377

2023.10.25

登录token无效
登录token无效

登录token无效解决方法:1、检查token的有效期限,如果token已经过期,需要重新获取一个新的token;2、检查token的签名,如果签名不正确,需要重新获取一个新的token;3、检查密钥的正确性,如果密钥不正确,需要重新获取一个新的token;4、使用HTTPS协议传输token,建议使用HTTPS协议进行传输 ;5、使用双因素认证,双因素认证可以提高账户的安全性。

6606

2023.09.14

C# ASP.NET Core微服务架构与API网关实践
C# ASP.NET Core微服务架构与API网关实践

本专题围绕 C# 在现代后端架构中的微服务实践展开,系统讲解基于 ASP.NET Core 构建可扩展服务体系的核心方法。内容涵盖服务拆分策略、RESTful API 设计、服务间通信、API 网关统一入口管理以及服务治理机制。通过真实项目案例,帮助开发者掌握构建高可用微服务系统的关键技术,提高系统的可扩展性与维护效率。

3

2026.03.11

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
C# 教程
C# 教程

共94课时 | 11.1万人学习

C 教程
C 教程

共75课时 | 5.3万人学习

C++教程
C++教程

共115课时 | 21.4万人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号