关于用信号量Semaphore实现互斥锁Mutex
import java.util.concurrent.Semaphore;
public class Mutex {
private Semaphore s = new Semaphore(1);
public void acquire() throws InterruptedException {
s.acquire();
}
public void release(){
s.release();
}
public boolean attempt(int ms) throws InterruptedException {
return s.tryAcquire(ms);
}
}
上面的代码只能在java5中编译通过,因为
Semaphore是在java5中才提供的。我在读上面的代码时有疑问。因为如果错误的连续调用release两次,然后两个线程都调用acquire,岂不是这两个线程都可以同时运行,从而违背了互斥锁的定义?为了证明我的猜测,写了如下的代码:
public class TestMutex {
public static void main(String[] args) throws InterruptedException{
Mutex mutex=new Mutex();
mutex.acquire();
mutex.release();
mutex.release();
new MyThread(mutex).start();
new MyThread(mutex).start();
}

}

class MyThread extends Thread{
private Mutex mutex;

public MyThread(Mutex mutex) {
this.mutex=mutex;
}

public void run(){
try {
mutex.acquire();
} catch (InterruptedException e1) {
throw new RuntimeException(e1);
}
for(int i=0;i<10;i++){
System.out.print(i);
if(i%3==0){
try {
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
mutex.release();
}
}
该程序的输出如下: 作为对比,下面是采用synchronized关键字的互斥锁方案: 该程序的输出如下:
00123123456456789789
从而证实了我的猜测。
public class TestLock {
public static void main(String[] args) throws InterruptedException{
new MyThread2().start();
new MyThread2().start();
}

}

class MyThread2 extends Thread{
public void run(){
synchronized(TestLock.class){
for(int i=0;i<10;i++){
System.out.print(i);
if(i%3==0){
try {
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
}
}
01234567890123456789
可见两个线程确实互斥运行。
这个问题产生的原因是虽然在Mutex的定义中"private Semaphore s = new Semaphore(1)",也就是该信号量的初始permits是1,但是在此后每次调用release方法都会导致permits加一。如果能限制permits最大值1,最小值0,那就是真正的Mutex了。
- (10-02-25 00-00)Javascript 操作select控件大全(新增、修改、删除、选中、清空、判断存在等)
- (10-02-25 00-00)信号量
- (10-02-25 00-00)远程执行本地命令
- (10-02-25 00-00)Onunload与Onbeforeunload
- (10-02-25 00-00)改变mysql数据包1M的限制
- (10-02-25 00-00)jQuery-位置选择器
- (10-02-25 00-00)jQuery-位置选择器
- (10-02-25 00-00)jQuery-创建元素包装集
- (10-02-25 00-00)jQuery-引荐
- (10-02-25 00-00)jQuery-AJAX
