//死锁,两个锁(两个互斥量),被两个线程按乱序使用导致死锁,跟解锁顺序无关
//死锁的解决办法一:保证两个互斥量上锁的顺序一致就不会死锁。
//解决方法二:std::lock()函数,一次锁住两个或两个以上的互斥量(至少两个,多了不限,1个不行);
//要么两个互斥量都锁住,要么两个互斥量都没锁住。如果只锁了一个,另外一个没锁成功,则它立即把已经锁住的互斥量解锁。
#include<iostream>
#include<thread>
#include<vector>//适合乱序取出数据
#include<list>//适合有序取出数据
#include<mutex>//互斥量
using namespace std;
class A {
public:
void inMsgRecvQueue()
{
for (int i = 0; i < 10000; i++)
{
cout << "Insert a number in inMsgRecvQueue():" << i << endl;
//死锁状态
//my_mutex.lock();
//函数处理数据
///.....
/// ......
/// .......
/// 开始处理第二个数据
//my_mutex2.lock();
//Guard 模式
//lock_guard<mutex>msgRecGuard(my_mutex);
//lock_guard<mutex>msgRecGuard2(my_mutex2);
//解决方法二:lock()解决方法,配合unlock
lock(my_mutex2, my_mutex);
msgRecvQueue.push_back(i);
//my_mutex.unlock();
//my_mutex2.unlock();
//方法二:不用unlock1的方法
lock_guard<mutex>msgRecGuAdopt(my_mutex, adopt_lock);//adopt_lock不调用构造,自动析构,adopt_lock是个结构体对象,标记作用,可选择性构造lock
lock_guard<mutex>msgRecGuAdopt2(my_mutex2, adopt_lock);
}
}
void outMsgRecvQueue()
{
int command = 0;
for (int i = 0; i < 10000; i++)
{
//封装判断
bool result = getTheNumber(command);
if (result == true)
{
cout << "outMsg running, get the number:" << command ;
//处理进行处理command数据
//...
}
else {
cout << "outMsg is running,but the list is empty!";
}
cout << endl;
}
}
private:
list<int>msgRecvQueue;
mutex my_mutex;//我的互斥量
mutex my_mutex2;//测试死锁
protected:
bool getTheNumber(int &command)//取command地址,所以修改了command的数据
{
//死锁状态
/*my_mutex2.lock();
my_mutex.lock();*/
//解决方法一
//lock_guard<mutex>getNum(my_mutex);
//lock_guard<mutex>getNum(my_mutex2);
my_mutex.lock();
my_mutex2.lock();
if (!msgRecvQueue.empty())
{
command = msgRecvQueue.front();//Return the first value of the msgRecvQueue,but front doesn't check data
msgRecvQueue.pop_front();//Delete the first number of the msgRQ
my_mutex2.unlock();
my_mutex.unlock();
return true;
}
my_mutex.unlock();
my_mutex2.unlock();
return false;
}
};
int main() {
A myobj;
thread myOutMsgObj(&A::outMsgRecvQueue, &myobj);
thread myInMsgObj(&A::inMsgRecvQueue, &myobj);
if(myInMsgObj.joinable())
myInMsgObj.join();
else
cout << "The myInMsg is joined!" << endl;
if (myOutMsgObj.joinable())
myOutMsgObj.join();
else
cout << "The myOutMsg is joined!" << endl;
}
死锁问题和解决方法+lock()函数
猜你喜欢
转载自blog.csdn.net/guanxunmeng8928/article/details/107962492
今日推荐
周排行