线程同步中方式对比

在多线程程序中,往往会遇到线程中资源同步问题,同步问题可以划分为两类,一类为共享一个资源,一类为给每个线程分配一个资源

 

一:给每个线程分配一个资源

1:定义线程变量,在变量名前面加上_thread,该变量就会申明为线程变量

但是同时C++中对__thread变量的使用有额外的限制:

 

1. 在C++中,如果要在定义一个thread-local变量的时候做初始化,初始化的值必须是一个常量表达式。 

2. __thread只能修饰POD类型,即不带自定义的构造、拷贝、赋值、析构的类型,不能有non-static的protected或private成员,没有基类和虚函数,因此对定义class做了很多限制。但可以改为修饰class指针类型便无需考虑此限制。

2:当线程变量是复杂的C++类变量时,即不能申明为_thread变量

线程变量对于其他线程是可见,同时我们可以延伸出例外一种方式来代替线程变量

ps:A是一个类,线程的数量为n

A a[n];

对每个线程映射一个ID,线程1只能访问a[1],线程2访问a[2],从而达到每个线程访问一个对应的一个线程变量

 

二:多个线程共享一个资源

多个线程共享一个资源涉及多种方式:信号量,互斥量,临界区,自旋锁,读写锁,条件变量

 

1:信号量

信号量主要用于同步,信号量在系统中可以被任意一个线程释放

 

三个操作:

1、一个信号量可以初始化为非负值

2、semWait操作可以使信号量减1,若信号量的值为负,则执行semWait的进程被阻塞。否则进程继续执行。

3、semSignal操作使信号量加1。若信号量的值小于等于0,则被semWait操作阻塞的进程讲被接触阻塞。

ps: semWait对应P原语,semSignal对应V原语。

 

即A线程调用 semWait,B线程调用semSignal,可以释放A线程,让A线程执行

 

2:互斥量

互斥量主要用于防止多个线程同时访问同一个资源

A线程加锁了,B线程无法释放A线程加的锁,只能等A线程自己释放

 

3:临界区

在多进程程序中,临界区申明的锁,只对当前进程有效,其他进程无效,信号量跟互斥锁对其他进程也是有效的,可以获取的

 

4:自旋锁

自旋锁加锁时不会让出cpu,一直会处于自旋状态去获取锁,互斥量跟临界区都是会进入休眠状态,把CPU让出,自旋锁适用高性能场景

 

5:读写锁

当线程A处于读的状态,线程B也可以读,但是不能写,当线程A处于写的状态,线程B则不能读,适用与少写多读的场景

 

6:条件变量

条件变量可以同时唤醒多个线程,信号量只能唤醒一个,唤醒多个线程的时候,通常涉及到资源竞争,往往配合互斥锁使用

 

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值