C++11与thread相关使用(纯代码)

本文介绍了C++中的多线程创建方法,包括使用普通函数、lambda表达式、线程锁mutex以及如何处理线程同步、异常死锁和原子操作。还探讨了线程引用和智能指针在避免并发问题中的应用。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

多线程创建 

//多线程创建
void print(string s)
{
	cout << "i am a new thread:" << s << endl;
}
int main()
{
	//move将左值变成右值(右值引用过后的属性是左值)
	//thread t1(print, "t1");
	//thread t2(move(t1));//调用移动构造
	//t2.join();

	//多线程创建
	vector<thread> vt(5);//创建无参的线程对象:即空线程,不会启动
	int i = 0;

	for (thread& t : vt)//没提供拷贝构造,使用引用
	{
		//移动赋值
		t = thread(print, "线程"+to_string(i++));//匿名对象 将亡值
	}
	for (thread& t : vt)
	{
		t.join();
	}

	return 0;
}


 lambda表达式作为线程参数

//lambda表达式作为线程参数

int main()
{
	int n = 100;
	auto f = [n](const string& s) mutable{
		for (int i = 0; i < n; i++)
		{
			//n++;//传值捕获参数具有const属性,不能修改,除非mutable修饰
			cout << i << ":i am a new thread:" << s << endl;
		}
	};
	//function<void(const string&)> pf = f;//包装器
	//pf("abc");
	//f("abc");

	thread t1(f,"t1");
	t1.join();

	return 0;
}


线程锁mutex
 

//线程锁mutex
int main()
{
	int n;
	cin >> n;
	int x = 0;

	//存在线程安全的问题
	//thread t1([n, &x] (){
	//	for (int i = 0; i < n; i++)
	//	{
	//		x++;
	//	}
	//	});
	//thread t2([n, &x]() {
	//	for (int i = 0; i < n; i++)
	//	{
	//		x++;
	//	}
	//	});

	mutex mx;//上锁(锁不支持拷贝)
	thread t1([n, &x,&mx]() {
		for (int i = 0; i < n; i++)
		{
			mx.lock();
			x++;
			mx.unlock();
		}
		});
	thread t2([n, &x,&mx]() {
		for (int i = 0; i < n; i++)
		{
			mx.lock();
			x++;
			mx.unlock();
		}
		});

	t1.join();
	t2.join();

	cout << "调用次数:" << x << endl;//只有线程执行完毕才是有效的x

	return 0;
}

 线程引用接收参数-----ref()

//线程引用接收参数-----ref()
void Count(int n, int& x)//thread的构造函数所调用的函数不能引用接收参数
{
	//thread构造函数内部是通过参数列表的方式解析传来的参数
	//而且传来的参数是传给构造函数的,而不是直接传给形参的,所以参数推导会出问题
	//实参加上ref修饰,或者形参const&修饰
	for (int i = 0; i < n; i++)
	{
		x++;
	}
}
int main()
{
	int x = 0;
	int n; cin >> n;
	thread t1(Count, n, ref(x));
	t1.join();
	cout << "循环次数:" << x << endl;

	return 0;
}


 异常死锁问题--》智能指针

//异常思索问题--》智能指针
void fun()
{
	srand(time(nullptr));//设置随机数种子
	
	while (1)
	{
		int x = rand() % 10;
		cout << x << ' ';
		if (x == 3)
		{
			throw exception("异常错误");
		}
		
	}
	cout << endl;
}

class guardlock
{
public:
	guardlock(mutex& m)
		:_m(m)//mutex不支持拷贝和赋值
	{
		_m.lock();
	}
	~guardlock()
	{
		_m.unlock();
	}
private:
	mutex& _m;//成员变量用引用
};
int main()
{
	mutex m;
	try {
		//guardlock gl(m);//不会死锁,最终栈销毁的时候都会先调用析构函数解锁
		//lock_guard<mutex> lg(m);//库中
		unique_lock<mutex> lg(m);//库中(支持手动上锁和解锁)
		fun();
	}
	catch (exception e)
	{
		cout << e.what() << endl;
	}

	return 0;
}

两个线程交替打印奇偶数-->atomic(底层cas) 


//两个线程交替打印奇偶数-->atomic(底层cas)
//do {//模拟x++
//	old = x;
//	newval = old + 1;
//} while (atomic_compare_exchange_weak(&x, &old, newval);

int main()
{
	mutex mx;
	int i = 0;
	//atomic<size_t> i = 0;//原子性的,不运行多执行流同时访问该资源
	condition_variable con1;
	condition_variable con2;
	thread t1([&mx, &i,&con1,&con2]() {
		while (i<=1000)
		{
			unique_lock<mutex> lg(mx);//局部变量,出了作用域自动调用析构
			if (i % 2 != 1)
				con1.wait(lg);
			if (i % 2 == 1)
			{
				cout << "t1:" << i << endl;
				i++;
			}
			con2.notify_one();
			//lg.unlock();
		}
	});

	thread t2([&mx, &i,&con1,&con2]() {
		while (i<=1000)
		{
			unique_lock<mutex> lg(mx);
			if (i % 2 != 0)
				con2.wait(lg);
			if (i % 2 == 0)
			{
				cout << "t2:" << i << endl;
				i++;
			}
			con1.notify_one();
			//lg.unlock();
		}

	});

	t1.join();
	t2.join();

	return 0;
}

C++创建的线程不join就会直接崩溃 

void print(string s)
{
	cout << s << endl;
}
int main()
{
	thread t1(print, "hah");
	//t1.join();

	return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

CR0712

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值