C++ 基础 day4 C++20新特性
4.23
1.模块
2.协程
3.<=> 三向比较运算符
4.范围
5.日期和时区
6.格式化
7.跨度
8.并发
1.模板
从 C 语言中,C++ 继承了** #include 机制**,依赖从头文件使用文本形式包含 C++ 源代码,这些头文件中包含了接口的文本定义。一个流行的头文件可以在大型程序的各个单独编译的部分中被 #include 数百次。
基本问题是:
(1) 不够卫生:一个头文件中的代码可能会影响同一翻译单元中包含的另一个 #include 中的代码的含义,因此 #include 并非顺序无关。宏是这里的一个主要问题,尽管不是唯一的问题。
(2) 分离编译的不一致性:两个翻译单元中同一实体的声明可能不一致,但并非所有此类错误都被编译器或链接器捕获。
(3) 编译次数过多:从源代码文本编译接口比较慢。从源代码文本反复地编译同一份接口非常慢。所以,在 C++ 程序中改进模块化是一个迫切的需求
ps:模块化是什么意思?顺序独立性:import X; import Y; 应该与 importY; import X; 相同。换句话说,任何东西都不能隐式地从一个模块“泄漏”到另一个模块。
1)创建模板
源文件->添加->新建项->Module
创建***.ixx文件
案例:
点击查看代码
//创建模块
// mymodule.ixx //模块名和文件名没有强制要求,一般会相同
export module helloworld; // 模块声明
import <iostream>; // 导入声明 注意;号
export void hello() { // 导出声明
std::cout << "Hello world!\n";
}
//导入模块
// main.cpp
import helloworld; // 导入声明
int main() {
hello();
}
2.协程(看不大懂
协程就是一个可以挂起(suspend)和恢复(resume)的函数(不能是 main 函数)。你可以暂停协程的执行,去做其他事情,然后在适当的时候恢复到暂停的位置继续执行。协程让我们用同步方式写异步代码
C++20 提供了三个新关键字(co_await、co_yield 和 co_return),如果一个函数中存在这三个关键字之一,那么
它就是一个协程。
1)co_yield some_value: 保存当前协程的执行状态并挂起,返回some_value给调用者
2)co_await some_awaitable: 如果some_awaitable没有ready,就保存当前协程的执行状态并挂起
3)co_return some_value: 彻底结束当前协程,返回some_value给协程调用者
3.<=> 三向比较运算
1)(a <=> b) < 0 // 如果 a < b 则为 true
2)(a <=> b) > 0 // 如果 a > b 则为 true
3)(a <=> b) == 0 // 如果 a 与 b 相等或者等价 则为 true
例子:
点击查看代码
int num1 = 100, num2 = 100;
if ((num1 <=> num2) < 0) {
cout << "num1 < num2" << endl;
}
else if ((num1 <=> num2) > 0) {
cout << "num1 > num2" << endl;
}
else {
cout << "num1 = num2" << endl;
}
4.范围 range
范围库始于 Eric Niebler 对 STL 序列观念的推广和现代化的工作。它
提供了更易于使用、更通用及性能更好的标准库算法。
例如,C++20 标准库为整个容器的操作提供了期待已久的更简单的
表示方法。(不用写怎么多了
点击查看代码
void func1(vector<string>& s) {
sort(s); // 而不是 sort(vs.begin(), vs.end());
}
点击查看代码
#include <vector>
#include <ranges>
#include <iostream>
using namespace std;
int main()
{
auto ints = views::iota(0, 10);//生成0-9
auto even = [](int i) { return 0 == i % 2; };
auto square = [](int i) { return i * i; };
for (int i : ints | views::filter(even)|views::transform(square))cout << i << ' ';//输出:0 4 16 36 64
return 0;
}
5.日期和时区
日期库是日期库是多年工作和实际使用的结果,它基于 chrono 标准库的时间支持。在 2018 年,它进入了 C++20,并和旧的时间工具一起放在
例子:
点击查看代码
void test13() {
//creating a year
auto y1 = year{ 2019 };
auto y2 = 2019y;
//creating a mouth
auto m1 = month{ 9 };
auto m2 = September;
//creating a day
auto d1 = day{ 18 };
auto d2 = 18d;
year_month_day date1{ 2022y,July,21d };
auto date2 = 2022y / July / 21d;
chrono::year_month_day date3{ Monday[3] / July / 2022 };
cout << date1 << endl;
cout << date2 << endl;
cout << date3 << endl;
return;
}
6.格式化
格式化库提供了一种类 printf 的方式去组装字符串和格式化输出值,同时这种方法类型安全、快捷,并能和 iostream 协同工作。类型中带有 << 运算符的可以在一个格式化的字符串中输出。
例子:
点击查看代码
string s1 =
"C++";
cout << format("The string '{}' has {} characters", s1, s1.size());
cout << format("The string '{0}' has {1} characters", s1, s1.size()) << endl;
cout << format("The string '{1}' has {0} characters", s1.size(), s1) << endl
7.跨度
越界访问,有时也称为缓冲区溢出,从 C 的时代以来就一直是一个严重的问题。考虑下面的例子:
点击查看代码
void func1(int* p, int n) { // n 是什么?
for (int i = 0; i < n; ++i) {
p[i] = 7; // 是否可行?
}
}
C++20
点击查看代码
span<T> 类模板就这样被放到 C++ 核心指南的支持库中。
void func(span<int> a) { // span 包含一个指针和一条大小信息
for (int& x : a) {
x = 7; // 可以
}
}
8.并发(没学过不看了
9.numbers 常用的数学常量
例子:
点击查看代码
#include <numbers>
void test11() {
cout << "numbers::e=" << numbers::e << " " << numbers::e_v<double> << endl;
cout << "numbers::log10e=" << numbers::log10e << " " << numbers::log10e_v<double> << endl;
}

浙公网安备 33010602011771号