综合 Toronto, Rapperswil, San Diego, Kona meeting 的结果, Modules, Ranges, Coroutines, Concepts, Contracts 都已经并入 C++20


Modules

Merging Modules

告别头文件,更快的编译速度,更好的build cache/可能的包管理。主要问题在于module mapping需要编译器和build system的协作,这一部分将来还有许多变数。

长话短说,直接上例子:

旧代码怎么转换成模块

include

这种方式include的header还会走旧的preprocessor一套。

包装代码:

module;
#include "some-header.h" //原有的老头文件, defines classes X, Y, Z
export module foo;
export using X = ::X; // export name X; retain all declarations
// of X from "some-header.h"
export Y f(); // export name f; retain all declarations
// of Y from "some-header.h"
// Z is not mentioned, so is discarded

// 或者
export import "another-header.h"; // another-header.h中的全部内容(除了宏)都会被导出

使用者:

import foo;
Y y = f();

import (推荐)

这种方式import的头文件是以模块方式编译的。

export module foo; // 提供了一个foo的模块
import "some_headers.h";
import &

这么写无需更改原来库的任何内容,"some_headers.h"里的所有声明 + 宏会被原样import进来。区别于现在的include的是:被import的对象是在一个单独的TU里翻译的,不会受到主文件中符号的干扰,可以更好的cache编译结果。

这种方式优点是完全无痛,缺点是还保留了原先的header文件,适合处理一些不方便包/改动的第三方库。

新代码

下面这个代码是一个moda模块可能的代码组织方式:

src/
|- moda/
|- functions.cpp
|- base.cpp
|- detail.cpp

base.cpp

export module moda:base; // users can import moda:base;

export void foo();
export int a;

functions.cpp

export module moda; // user can import moda

export import :base; // export all functions and values in base
// Moreover, moda.a is the same entity with moda.base.a
import :detail; // detail will not be exposed
export void additionalF() { implF(); }

detail.cpp

module moda:detail; //external user cannot import this module, only use through functions.cpps additionalF()
#include "some-macro.h" // legacy import, can import macro
import &; // atom-style import. Cant import macro in this way
void somelocalStuffs();
export void implF() {};

Coroutine

Coroutine

这次merge的是无栈版协程。直接看 What are coroutines in C++20? 这个

// Credits: http://www.modernescpp.com/index.php/coroutines

Acceptor acceptor{443};
while (true){
Socket socket= co_await acceptor.accept();
auto request= co_await socket.read();
auto response= handleRequest(request);
co_await socket.write(responste);
}

generator& generatorForNumbers(int begin, int inc= 1){
for (int i= begin;; i += inc){
co_yield i;
}
}

int main() {
std::cout &

std::polymorphic_allocator&

http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2018/p0339r5.pdf?

www.open-std.org

之前有的polymorphic_allocator&为什么还要存在&这样一个类型参数?反正都要到处rebind,不如直接提供一个裸分配byte chunks的介面:polymophic_allocator&

剩下几个之前的文章里都介绍过:

Unwinding the stack?

zhuanlan.zhihu.com图标

其实吧,这些大家都是巴不得17年就进来的(还包括networking)。现在搞到20年才进来,23年networking才有可能,已经在大家期待之外了。要问怎么看,只能说来得太晚了。

虽然编译器很多功能都已经实现了,但是没进标准,是没有任何公司敢在真正的项目中用的。


好开心,可以直接从20开始入门了


Q:你会C++吗?

A:会过。


如果我仅仅说好,这表达了我有多么的被动。事实上,加的越多越好。

原来就是因为功能少,不方便,导致没人用,都去搞其他语言了。

这回好了。彻底消灭精通c++的程序员。


到能用上要等多少年呢


这东西对于新手的准入门槛已经太高了,还是建议采取C+动态脚本语言来解决问题,代码简洁,边界清晰,最主要是对于代码的控制力强,非常舒服


推荐阅读:
相关文章