gpt4 book ai didi

c++ - 使用 C++ notify_all() 避免饥饿

转载 作者:搜寻专家 更新时间:2023-10-31 02:19:55 27 4
gpt4 key购买 nike

我的屏障同步场景是这样的:

一个。线程在同步中向前迈进了一步 - 即它们完成一个任务单元,然后等待所有其他线程执行相同的操作,然后当它们完成时,它们可以再次向前移动。

我有大量线程(大约 256 个)在等待条件变量。满足条件时,将发送 notify_all()

(出现饥饿风险的部分):在 notify_all() 被调用之前,一个 runnable 变量被设置为 true 和一个计数器 - completed - 设置为零。当一个线程完成它的任务单元时,它调用一个函数,该函数首先将 runnable 设置为 false,然后递增 completed 变量 - 满足条件当 completed 等于阈值(即需要完成任务单元的线程数)时,runnable 设置为 true。

即,我们这样等待:

cond.wait(lck, runnable == true);

还有这个:

unique_lock<mutex> lck(runMut);
runnable = true;
cond.notify_all();

我担心的是,任何被唤醒的线程都可以完成其任务,然后在链中更下游的线程被唤醒之前调用 wait() 函数。当这个“下层”线程测试 runnable 时,它会发现它设置为 false 并因此返回休眠。

是否有设计模式或其他方法可以解决这个问题?

最佳答案

您可以使用两个条件变量。一个通知 worker 开始工作,另一个通知 worker 已经完成。 IE。你的主线程看起来像这样:

for (;;) {
running = 0;
done = 0;
cond_run.notify_all();
cond_done.wait(lck, []() { return done == threads; });
// handle results
}

你的工作线程看起来像这样:

for (;;) {
cond_run.wait(lck, []() { return running < threads; });
++running;
lck.unlock();
// do work
lck.lock():
++done;
cond_done.notify_one();
}

关于c++ - 使用 C++ notify_all() 避免饥饿,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33335167/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com