互斥锁mutex/lock_guard/unique_lock

2022-06-01  本文已影响0人  九楼记

互斥锁

互斥锁的应用场景,对共享的数据进行写保护,以防止多线程在对共享数据成员进行读写时造成资源争抢导致程序出现未定义的行为。

简单例子

先看一段代码

#include <iostream>
#include <thread>
#include <string>
using namespace std;

void Print()
{
    for (int i = 0; i < 10; i++) {
        cout << "print thread: " << i << endl;
    }
}
int main()
{
    thread t(Print);
    for (int i = 0; i > -10; i--) {
        cout << "print main: " << i << endl;
    }
    t.join();
    return 0;

}

因为多线程执行的顺序,是CPU根据时间片随机调度的,每次执行顺序不固定,输出结果也不定。
怎么可以固定下来呢?
用互斥锁。

用互斥锁的例子

#include <iostream>
#include <thread>
#include <mutex>
#include <string>
using namespace std;

mutex mtx;
void Print()
{
    mtx.lock();
    for (int i = 0; i < 10; i++) {
        cout << "print thread: " << i << endl;
    }
    mtx.unlock();
}
int main()
{
    thread t(Print);
    mtx.lock();
    for (int i = 0; i > -10; i--) {
        cout << "print main: " << i << endl;
    }
    mtx.unlock();
    t.join();
    return 0;

}

互斥锁的用法

std::mutex 是C++11 中最基本的互斥锁,std::mutex 对象提供了独占所有权的特性——即不支持递归地对
std::mutex 对象上锁,而 std::recursive_lock 则可以递归地对互斥量对象上锁。
成员函数:lock、unlock、try_lock
除了mutex类,c++11还提供了lock_guard和unique_lock。

lock_guard

std::lock_gurad 是 C++11 中定义的模板类。定义如下:

template <class Mutex> 
class lock_guard;

lock_guard 对象通常用于管理某个锁(Lock)对象,因此与 Mutex RAII 相关,方便线程对互斥量上锁,即在某个 lock_guard 对象的声明周期内,它所管理的锁对象会一直保持上锁状态;而 lock_guard 的生命周期结束之后,它所管理的锁对象会被解锁(注:类似 shared_ptr 等智能指针管理动态分配的内存资源 )。

值得注意的是,lock_guard 对象并不负责管理 Mutex 对象的生命周期,lock_guard 对象只是简化了 Mutex 对象的上锁和解锁操作,方便线程对互斥量上锁,即在某个 lock_guard 对象的声明周期内,它所管理的锁对象会一直保持上锁状态;而 lock_guard 的生命周期结束之后,它所管理的锁对象会被解锁。

特点:

unique_lock

虽然lock_guard挺好用的,但是有个很大的缺陷,在定义lock_guard的地方会调用构造函数加锁,在离开定义域的话lock_guard就会被销毁,调用析构函数解锁。这就产生了一个问题,如果这个定义域范围很大的话,那么锁的粒度就很大,很大程序上会影响效率。

lock_guard最大的缺点也是简单,没有足够的灵活度。
unique_lock 对象以独占所有权的方式( unique owership)管理 mutex 对象的上锁和解锁操作,所谓独占所有权,就是没有其他的 unique_lock 对象同时拥有某个 mutex 对象的所有权。

和 lock_guard 一样,这也是一种简单而又安全的上锁和解锁方式,尤其是在程序抛出异常后先前已被上锁的 Mutex 对象可以正确进行解锁操作,极大地简化了程序员编写与 Mutex 相关的异常处理代码。

Reference

[1] https://zhuanlan.zhihu.com/p/340154702
[2] https://blog.csdn.net/zzhongcy/article/details/85230200
[3] https://zhuanlan.zhihu.com/p/340348726
[4] https://www.jianshu.com/p/b67cc7b40a1e

上一篇 下一篇

猜你喜欢

热点阅读