如何在c++ 11中防止线程饥饿

How to prevent threads from starvation in C++11

本文关键字:线程 饥饿 c++      更新时间:2023-10-16

我只是想知道c++ 11中是否有任何锁定策略可以防止线程饥饿。

我有一堆线程在竞争一个互斥锁。现在,我的问题是,离开临界区的线程立即开始争夺同一个互斥锁,而且大多数时候都是胜利的。因此,等待互斥锁的其他线程正在挨饿。

我不想让线程,留下一个临界区,休眠一些最小的时间给其他线程一个锁定互斥锁的机会。

我认为一定有一些参数可以为等待互斥锁的线程提供公平的锁定,但我找不到任何合适的解决方案。

我发现std::this_thread::yield()函数,它假设重新调度线程执行的顺序,但它只是提示调度线程,取决于调度线程实现是否重新调度线程。

在c++ 11中,是否有办法为等待同一互斥锁的线程提供公平的锁定策略?通常的策略是什么?

谢谢

这是互斥锁中常见的优化,旨在避免在同一个线程可以再次使用互斥锁时浪费时间切换任务。如果当前线程的时间片还有剩余时间,那么通过让它获取互斥锁而不是挂起互斥锁,并切换到另一个线程(这可能会导致大量重新加载缓存线和各种其他延迟),就每秒执行的用户指令而言,您可以获得更多的吞吐量。

如果你在一个互斥对象上有太多的争用,这是一个问题,那么你的应用程序设计是错误的。所有这些线程都阻塞在互斥锁上,因此没有做任何事情:没有这么多线程可能会更好。

你应该设计你的应用程序,这样如果多个线程竞争一个互斥锁,那么哪个线程获得锁并不重要。直接争用也应该是一种罕见的事情,特别是与大量线程的直接争用。

我认为这是一个OK的场景的唯一情况是每个线程都在等待一个条件变量,然后广播以唤醒它们。然后每个线程都将争用互斥锁,但是如果您做得对,那么它们都应该快速检查这不是一个虚假的唤醒,然后释放互斥锁。即使在这种情况下,这也被称为"thunderming herd"情况,这并不理想,因为它将所有这些线程序列化。