同步工具类之Semaphore
2017-01-09 本文已影响9人
evil_ice
一,计数信号量(Counting Semaphore)概述
- 计数信号量(Counting Semaphore)用来控制同时访问某个特定资源的操作数量,或者同时执行某个指定操作的数量.计数信号量还可以用来实现某种资源池,或者对容器施加边界
- Semaphore中管理着一组虚拟的许可(Permit),许可的初始数量可通过构造函数来指定.在执行操作时可以首先获得许可(只要还有剩余的许可),并在使用以后释放许可.如果没有许可,那么acquire将阻塞直到有许可(或者直到被中断或者操作超时).release方法将返回一个许可信号量.
- 计数信号量的一种简化形式是二值信号量,即初始值为1的Semaphore,二值信号量可以用做互斥体(mutex),并具备不可重入的加锁语义:谁拥有这个唯一许可,谁就拥有了互斥锁
- 可以使用Semaphore将任何一种容器编程有界阻塞容器
二,利用Semaphore实现一个有界阻塞容器示例
信号量的计数值会初始化为容器容量的最大值.add操作在向底层容器中添加一个元素之前,首先要获取一个许可.如果add操作没有添加任何元素,那么会立刻释放许可.同样,remove操作释放一个许可,使更多的元素能够添加到容器中.
class BoundedHashSet<T> {
private final Set<T> set;
private final Semaphore sem;
public BoundedHashSet(int bound) {
this.set = Collections.synchronizedSet(new HashSet<T>());
sem = new Semaphore(bound);
}
public boolean add(T o) throws InterruptedException {
sem.acquire();
boolean wasAdded = false;
try {
wasAdded = set.add(o);
return wasAdded;
} finally {
if (!wasAdded) {
sem.release();
}
}
}
public boolean remove(Object o) {
boolean wasRemoved = set.remove(o);
if (wasRemoved) {
sem.release();
}
return wasRemoved;
}
}
参考:
<<java编发编程实战>>