C++ 全栈知识体系C++ 全栈知识体系
✿导航
  • 基础
  • 函数
  • 知识点
  • IO框架
  • 新版本特性
  • 数据库原理
  • SQL语言
  • SQL - MySQL
  • NoSQL - Redis
  • NoSQL - ElasticSearch
  • 算法基础
  • 常见算法
  • 领域算法
  • 分布式算法
  • 数据结构与算法
  • 计算机网络
  • 操作系统
  • 计算机组成
  • 开发
  • 测试
  • 架构基础
  • 分布式系统
  • 微服务
  • 中间件
  • 概念
  • 理论
  • 架构设计原则
  • 设计模式
  • 协议
  • 技术选型
  • 编码规范
  • 流水线构建 - CI/CD
  • 知识点 - Linux
  • 网站 - Nginx
  • 容器化 - Docker
  • 容器编排 - Kubernetes
  • 服务网格 - Service Mesh Istio
  • 常用快捷键 - Shortcut
  • 工具使用 - Tools
  • 开源项目
  • 学习项目
  • 个人项目
  • 项目开发
  • 项目Idea
  • 并发
  • 部署
  • 分布式
  • 知识
  • 问题
  • 编程语言与技术
  • 系统与架构
  • 软件开发实践
  • 数据处理与应用设计
  • 个人
  • 产品
  • 团队
  • 知识体系
  • Vue
关于
✿导航
  • 基础
  • 函数
  • 知识点
  • IO框架
  • 新版本特性
  • 数据库原理
  • SQL语言
  • SQL - MySQL
  • NoSQL - Redis
  • NoSQL - ElasticSearch
  • 算法基础
  • 常见算法
  • 领域算法
  • 分布式算法
  • 数据结构与算法
  • 计算机网络
  • 操作系统
  • 计算机组成
  • 开发
  • 测试
  • 架构基础
  • 分布式系统
  • 微服务
  • 中间件
  • 概念
  • 理论
  • 架构设计原则
  • 设计模式
  • 协议
  • 技术选型
  • 编码规范
  • 流水线构建 - CI/CD
  • 知识点 - Linux
  • 网站 - Nginx
  • 容器化 - Docker
  • 容器编排 - Kubernetes
  • 服务网格 - Service Mesh Istio
  • 常用快捷键 - Shortcut
  • 工具使用 - Tools
  • 开源项目
  • 学习项目
  • 个人项目
  • 项目开发
  • 项目Idea
  • 并发
  • 部署
  • 分布式
  • 知识
  • 问题
  • 编程语言与技术
  • 系统与架构
  • 软件开发实践
  • 数据处理与应用设计
  • 个人
  • 产品
  • 团队
  • 知识体系
  • Vue
关于
  • 基础

    • C++ 基础 - 学习路线
    • C++ 基础 - 知识点
    • C++ 基础 - 面向对象
    • C++ 基础 - 语法糖
    • C++ 基础 - 关键字
    • C++ 基础 - 常用宏定义
    • C++ 基础 - 宏函数、内联函数、普通函数
  • 函数

    • C++ 函数 - 闭包
    • C++ 函数 - Linux系统调用Hook
    • C++ 函数 - getopt函数分析以及命令行解析
    • C++ 函数 - 函数指针及其应用
    • C++ 函数 - 作用域运算符::的使用
    • C++ 函数 - 智能指针shared_ptr的使用
    • C++ 函数 - struct结构体学习
    • C++ 函数 - typedef 语句的使用
    • C++ 函数 - va_list函数学习
  • 知识点

    • C++ 知识点 - 写时拷贝技术(copy-on-write)
    • C++ 知识点 - 前向声明(forward declaration)
    • C++ 知识点 - 头文件.h 和 源文件.cpp 以及多重定义(multiple definition)
    • C++ 知识点 - 为什么C语言不支持函数重载,C++又是如何支持的
    • C++ 知识点 - return 局部变量
    • C++ 知识点 - linux下c/cplusplus头文件和动态库的搜索
    • C++ 知识点 - 模板特化与偏特化
  • IO框架

    • C++ IO框架 - I/O 复用
    • C++ IO框架 - select 函数
    • C++ IO框架 - poll 函数
    • C++ IO框架 - epoll 函数
    • C++ IO框架 - Reactor 和 Proactor
  • 新版本特性

    • C++ 新版本特性 - C++11
    • C++ 新版本特性 - C++14
    • C++ 新版本特性 - C++17
    • C++ 新版本特性 - C++20

C++ 新版本特性 - C++20

  • Concepts
  • Range library
  • Coroutines
  • Modules
  • 特性测试宏
  • 三路比较运算符<=>
  • 范围for循环初始化

警告

C++20下面的代码未在环境上编译测试使用,仅用于理论知识补充,后期升级gcc版本再进行实测。

参考资料

  • cpp20

特性概览

c++20_1

c++20_2

c++20_3

The Big Four

Concepts

C++中模板编程极大地简化了代码的编写,但同时也会带来一些使用上的疑惑,例如,判断两个数是否相等,C++17提供了concept机制,用来检查模板参数类型:

详情
#include <concepts>
#include <iostream>

template <typename T>
concept Integeral = std::is_integral<T>::value;

template <Integeral T>
auto isEqual(T left, T right) {
  return left == right;
}

int main() {
  cout << std::boolalpha;

  double a = 2.334;
  double b = 2.335;

  std::cout << isEqual(2, 2) << std::endl;         // true
  std::cout << isEqual(b - a, 0.001) << std::endl; // false

  return 0;
}

Range library

ranges:代表一段元素,之前版本使用begin和end标识一段元素。

ranges优点:

  • 简化语法和操作;
  • 防止begin,end迭代器的不配对使用;
  • 使得类似管道|的串行操作成为可能。

相关概念:

  • View:延迟计算,只有读权限
  • Actions:即时处理,读或写
  • Algorithms:操作range
  • Views和Actions的串联操作
详情
#include <concepts>
#include <iostream>

//简化操作:
void simple_action()
{
  std::cout << "simple_action" << std::endl;
  std::vector<int> vec{3, 1, 2, 5, 6, 4};

  // std::sort()
  std::sort(vec.begin(), vec.end());
  std::copy(vec.begin(), vec.end(), std::ostream_iterator<int>{cout, " "}); // 1 2 3 4 5 6

  // ranges::sort()
  std::ranges::sort(vec);
  std::ranges::copy(vec, std::ostream_iterator<int>{cout, " "}); // 1 2 3 4 5 6
}

//串联视图:
void view_action()
{
  std::cout << "view_action" << std::endl;
  std::vector<int> vec{1, 2, 3, 4, 5, 6};

  auto even = [](int i){ return i % 2 == 0; };
  auto square = [](int i){ return i * i; };

  auto result = vec | std::views::filter(even) | std::views::transform(square);
  /* 此时 result 并没有被计算,只是定义了一系列视图,只有到下面的遍历操作时,result 触发,即所谓延迟计算 */
  for (auto i : result)
  {
    cout << i << " "; // 4 16 36
  }
}

//过滤和变换:
void filter_transfrom_action()
{
  std::cout << "filter_transfrom_action" << std::endl;

  std::vector vec{1, 2, 3, 4, 5};

  auto result = vec | std::views::transform([](int i){ return i * i; }) | std::views::take(3);

  cout << std::accumulate(result.begin(), result.end(), 0) << endl; // 14
}

int main()
{
  simple_action();
  view_action();
  filter_transfrom_action();

  return 0;
}

Coroutines

所谓协程,是一个函数,能在保持状态的时候暂停或者继续。具有关键字:

  • co_await:挂起协程,等待其它计算完成
  • co_return:退出协程
  • co_yield:弹出一个值,挂起协程,等待下一次调用,类似于Python中的生成器

待补充内容

Modules

关键字:import,export

新建测试文件test_module.ixx和main.cpp,注意模块文件后缀名为.ixx,如果为.cpp文件可能需要去命令行编译,使用方式和include差不多,但是说使用模块比使用include效率要高很多:

详情
// test_module.ixx
export module test_module;

namespace _module {
auto _print() { return "hello world"; }
export auto print() { return _print(); }
} // namespace _module

/*——————————————————————————————————————————*/

// main.cpp
import test_module;
#include <iostream>

int main() {
  std::cout << _module::print() << std::endl; // hello world
  return 0;
}

模块优势:

  • 没有头文件
  • 声明和实现仍然可以分离,但没有必要
  • 可以显式指定导出目标对象(函数,类)
  • 没有头文件重复包含风险
  • 模块名称可以相同
  • 模块只处理一次,编译更快(头文件每次引入都需要处理)
  • 预处理宏只在模块内有效
  • 模块引入顺序无关紧要

Core Language

特性测试宏

通过它可以判断编译器是否支持某个功能,例如:

// 语言特性
__has_cpp_attribute(fallthrough)
__cpp_binary_literals
__cpp_char8_t
__cpp_coroutines
// 标准库特性
__cpp_lib_concepts
__cpp_lib_ranges
__cpp_lib_scoped_lock

三路比较运算符<=>

(x <=> y) < 0 // 如果 x < y, 返回 true
(x <=> y) > 0 // 如果 x > y, 返回 true
(x <=> y) == 0 // 如果 x == y, 返回 true

可以使用以下代码代替所有的比较运算符:

auto X::operator<=>(const X&) = default;

范围for循环初始化

class Data {
public:
  Data(){}
  Data getData() { return Data(); }
private:
  std::vector<int> values;
};

int main() {
  for (auto data = getData(); auto &value : data.values) {
    cout << value << " ";
  }

  return 0;
}

待补充

Last Updated:
Contributors: klc407073648
Prev
C++ 新版本特性 - C++17