C++ 多线程
1. 使用原因
1.任务分解:耗时任务,任务分解,实时响应
2.数据分解:充分利用多核心CPU
3.数据流分流
2.核心概念
1.std::thread 基础
join():主线程等待阻塞子线程完成后,回收子线程资源,线程生命周期受控;
detach(): 子线程与主线程分离,子线程后台游离运行。主线程销毁后,子线程会强行销毁。如果访问y
1 |
|
2.Mutex & RAII 锁

mutex (互斥量)类型:允许多个线程安全访问变量
1 | lock() try_lock() unlock() |
mutex
recursive_mutex :用来解决递归调用lock_guard(mtx)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16class DoSomething{
public:
int fun1(){
std::lock_guard lock(mtx);
count*=2;
fun2();
return count;
}
int fun2(){
std::lock_guard lock(mtx);
count++;
}
private:
recursive_mutex mtx;//如果是mutex 会阻塞主线程
int count = 0;
}
timed_mutex:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43class TryDemo
{
public:
void print() {
for (int i = 0; i < 10; i++)
{
//
auto deadline = std::chrono::steady_clock::now() + std::chrono::milliseconds(100);
unique_lock<timed_mutex> lock(m_mutex, defer_lock);
if (lock.try_lock_for(100ms)) {
{
std::lock_guard guard(cout_mutex);
cout << "[" << this_thread::get_id() << "]" << "成功;\n";
}
this_thread::sleep_for(100ms);
}
else {
lock_guard guard(cout_mutex);
cout << "[" << this_thread::get_id() << "]" << "失败;\n";
this_thread::sleep_for(100ms);
}
}
}
private:
timed_mutex m_mutex;
mutex cout_mutex;
int m_count = 0;
};
int main(void)
{
TryDemo demo;
auto print = [](TryDemo& demo)
{demo.print(); };
thread t1(print, ref(demo));
thread t2(print, ref(demo));
t1.join();
t2.join();
}lock try_lock try_lock_for try_lock_until unlock
shared
1.如果只是用mutex会忘记没有解锁,2出现异常也不会解锁。导致永久阻塞所以引进
引入锁包装:
- lock_guard; 相当通过RAII 将mutex 的lock() 和unlock() 封装了,离开作用域后析构函数调用unlock()
1 | template <typename Mutex> |
- unique_lock:相比lock_guard 更加灵活,可以实现延迟加锁或者超时的加锁。
lock() try_lock try_lock_for try_lock_until(计时锁) unlock
- scoped_lock;
死锁预防
- lock()同时锁多个
- std::lock_guard顺序
3.Condition Variable
4.Condition Variable
5. autmic & Memory
6. Lock-Free 数据结构
7.Future/Promise/Async
8.ThreadPool & JobSystem
9.游戏引擎多线程模式
本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来源 Never Settle!
评论