Lock vs Semaphore vs Condition Variable vs Monitor(中文)

目录

1. Critical Section(CS)

2. Lock

3. Semaphore

4. Condition variable

5. Monitor

6. 总结


在多线程(并发)程序中,多个线程会访问同一个共享内存,为了避免产生一些奇怪的结果,这些线程应该按照合适的顺序访问共享内存,这个过程称为同步(synchronization)。可是仅仅保持同步还不够,为了让同步更加高效,多个线程互相之间也要保持交流。这篇文章主要讨论线程同步(synchronization)和交流(communication)。

1. Critical Section(CS)

临界区(Critical section)是程序的一段代码块,临界区不能被多个线程在同一时间访问,临界区的访问是互斥的,某一时刻最多只能有一个线程能进临界区。

2. Lock

Lock,叫做锁,提供了一种互斥的方式,Lock能保证某一时刻只有一个线程能进入到临界区(CS),如下面的伪代码:

Lock num_mutex; // num_mutex 是一个Lock对象
 
######################################
 
 
Thread1:
 
// 获取锁
mutex_lock(&num_mutex);
 
// ******** 临界区 *******
num++;
// ******** 临界区 *******
 
// 释放锁
mutex_unlock(&num_mutex); 
 
 
######################################
 
 
Thread2:
 
// 获取锁
mutex_lock(&num_mutex);
 
// ******** 临界区 *******
num++;
// ******** 临界区 *******
 
// 释放锁
mutex_unlock(&num_mutex);

在上面的伪代码中,num++ 不是原子性操作,所以 num++ 不能同时被两个线程执行。 当Thread1和Thread2同时获取锁,只有一个线程最终能获取锁,然后获取到锁的线程进入临界区(执行num++),另一个线程必须一直等待到锁被释放。

再来看下经典的生产者-消费者问题,用Lock可以解决这个问题,如下代码:

Lock count_mutex; // count_mutex 是一个Lock对象

int count = 0; // 待消费的商品数量
 
 
#############################################
 
 
 
Producer Thread
 
// 获取锁
mutex_lock(&count_mutex);
 
// 如果count等于 MAX_SIZE, 不能生产,需要等待
while(count == MAX_SIZE){
    
    // 释放锁,将锁让给Consumer
    mutex_unlock(&count_mutex);
 
    Thread.sleep(3000); // 睡眠3秒
    
    // 睡眠唤醒之后,再次获取锁
    mutex_lock(&count_mutex);
}
 
// ***** 临界区 ****//
 
// 生产
produce();
 
// 生产之后,count加1
count++;
 
// ***** 临界区 ****//
 
// 生产之后释放锁
mutex_unlock(&count_mutex);
 
 
 
##############################################
 
 
Consume
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值