与互斥锁相比,自旋锁是否保证上下文切换
Do spinlocks guarantee context switching when compared to mutexes
考虑以下代码片段
int index = 0;
av::utils::Lock lock(av::utils::Lock::EStrategy::eMutex); // Uses a mutex or a spin lock based on specified strategy.
void fun()
{
for (int i = 0; i < 100; ++i)
{
lock.aquire();
++index;
std::cout << "thread " << std::this_thread::get_id() << " index = " << index << std::endl;
std::this_thread::sleep_for(std::chrono::milliseconds(500));
lock.release();
}
}
int main()
{
std::thread t1(fun);
std::thread t2(fun);
t1.join();
t2.join();
}
我使用用于同步的互斥量获得的输出是第一个线程 1 完全执行,然后是线程 2。
在使用自旋锁(使用 std::atomic_flag 实现)时,我得到交错的线程之间的执行顺序(线程 1 的一次迭代后跟线程 2 的另一次迭代)。后一种情况的发生与我在执行迭代时添加的延迟无关。
我明白互斥量只保证互斥,不保证执行顺序。我的问题是,如果我想要一个执行顺序,使两个线程以交错方式执行,使用自旋锁是否是推荐的策略?
The output that I get with a mutex ... is first thread 1 [runs through the whole loop] followed by thread 2.
那是因为你的循环使用锁的方式:循环体做的最后一件事是解锁锁。它在下一次迭代开始时所做的下一件事是,它再次锁定锁。
另一个线程可以被阻塞,有效休眠,等待互斥体。当您的线程 1 释放锁时,OS 调度程序可能仍然是 运行 它的算法,试图弄清楚当线程 1 出现并再次锁定锁时如何响应。
这就像一场锁定互斥量的比赛,枪响时线程1在起跑线上,而线程2坐在板凳上系鞋带。
While using a spinlock...the order of execution between the threads which is interleaved
那是因为 "blocked" 线程并没有真正被阻塞。它在等待时仍在不同的处理器上活跃 运行。当第一个线程释放它时,它有更好的机会赢得锁。
考虑以下代码片段
int index = 0;
av::utils::Lock lock(av::utils::Lock::EStrategy::eMutex); // Uses a mutex or a spin lock based on specified strategy.
void fun()
{
for (int i = 0; i < 100; ++i)
{
lock.aquire();
++index;
std::cout << "thread " << std::this_thread::get_id() << " index = " << index << std::endl;
std::this_thread::sleep_for(std::chrono::milliseconds(500));
lock.release();
}
}
int main()
{
std::thread t1(fun);
std::thread t2(fun);
t1.join();
t2.join();
}
我使用用于同步的互斥量获得的输出是第一个线程 1 完全执行,然后是线程 2。 在使用自旋锁(使用 std::atomic_flag 实现)时,我得到交错的线程之间的执行顺序(线程 1 的一次迭代后跟线程 2 的另一次迭代)。后一种情况的发生与我在执行迭代时添加的延迟无关。
我明白互斥量只保证互斥,不保证执行顺序。我的问题是,如果我想要一个执行顺序,使两个线程以交错方式执行,使用自旋锁是否是推荐的策略?
The output that I get with a mutex ... is first thread 1 [runs through the whole loop] followed by thread 2.
那是因为你的循环使用锁的方式:循环体做的最后一件事是解锁锁。它在下一次迭代开始时所做的下一件事是,它再次锁定锁。
另一个线程可以被阻塞,有效休眠,等待互斥体。当您的线程 1 释放锁时,OS 调度程序可能仍然是 运行 它的算法,试图弄清楚当线程 1 出现并再次锁定锁时如何响应。
这就像一场锁定互斥量的比赛,枪响时线程1在起跑线上,而线程2坐在板凳上系鞋带。
While using a spinlock...the order of execution between the threads which is interleaved
那是因为 "blocked" 线程并没有真正被阻塞。它在等待时仍在不同的处理器上活跃 运行。当第一个线程释放它时,它有更好的机会赢得锁。