c++20 关于多线程并发新增了 latch, barrier, semaphore ,接下来就按照一个一个进行介绍
latch 是一次性使用的线程协调点, 一旦给定数量的线程达到latch点时, 所有线程都会解除阻塞, 并继续执行. 基本上它是一个计数器, 在每个线程到达latch点时倒数, 一旦计数器达到0, latch 将无限制保持在一个有信号的状态, 所有阻塞线程都将解除阻塞, 随后到达latch点的任何线程会立刻被允许执行.
latch 由 std::latch实现, 在
代码如下:
#include
#include
#include
#include
#include
#include
int main()
{
std::vector threads;
std::latch startLatch{ 1 };
for (int i = 0; i < 10; ++i)
{
threads.push_back(std::jthread{[i, &startLatch]{
std::cout<< i <<" in wait" <
clang++ -std=c++20 -pthread latch.cpp
barrier 是由一系列阶段组成的可重用线程协调机制, 允许多线程在barrier点阻塞. 当给定数量的线程到达barrier时, 将执行完成阶段的回调, 解除所有阻塞线程的阻塞, 重制线程技术器, 并开始下一个阶段. 在每隔阶段中, 可以调整下一个阶段的预期线程数. barrier对于在循环之间执行同步非常有用. 例如假设多线程并发执行, 并在一个循环中执行一些计算. 进一步假设一旦这些计算执行完成, 需要在线程开始其循环的新迭代之前对结果进一步处理. 对于这种情况, 设置barrier是完美的, 所有的线程都会阻塞在barrier处, 当它们全部到达时, 完成阶段回调将处理结果, 然后解除所有阻塞, 以开始它们的下一次迭代.
barrier 由 std::barrier实现, 在
下边是具体代码示例
#include
#include
#include
#include
#include
void completionFunction() noexcept
{
}
int main()
{
const size_t numberOfThreads{4};
std::barrier barrierPoint {numberOfThreads, completionFunction};
std::vector threads;
for (int i = 0; i < numberOfThreads; ++i)
{
threads.push_back(std::jthread{[i,&barrierPoint](std::stop_token token){
while (!token.stop_requested())
{
std::cout<
clang++ -std=c++20 -pthread barrier.cpp
semphore 信号量 是轻量级同步原语, 可用作其他同步机制(如mutex, latch, barrier)的构建块. 基本上上一个semaphore由一个表示很多插槽的计数器组成. 计数器在构造函数中初始化. 如果获得了一个插槽, 计数器就减少, 而释放插槽将增加计数器. 在
代码如下:
#include
#include
#include
#include
int main()
{
std::counting_semaphore semaphore{4};
std::vector threads;
for (int i = 0; i < 4; i++)
{
threads.push_back(std::jthread{[&semaphore](){
semaphore.acquire();
semaphore.release();
}});
}
}
clang++ -std=c++20 -pthread barrier.cpp