关于concurrent的子包locks下reentrantReadwritelock的一点疑惑

来源:互联网 发布:如何选购基金知乎 编辑:程序博客网 时间:2024/06/04 23:21

   今天想做个关于reentrantReadWritelock的demo,看下读读不互斥,读写互斥,写写互斥的情况,但是弄完demo之后,有个小困惑不能理解,不得已,csdn上来试一试,希望得到一些指导,先上demo相关的代码

package ReenTrantLock;

import java.util.concurrent.locks.ReentrantReadWriteLock;


public class ReadWriteLockTest {

static ReentrantReadWriteLock lock = new ReentrantReadWriteLock();

public staticvoid main(String[] args) {

// TODO Auto-generated method stub

Mythread t1 = new Mythread(0,"t1");

Mythread t2 = new Mythread(0,"t2");

Mythread t3 = new Mythread(1,"t3");

t1.start();

t2.start();

t3.start();


}

private staticclass Mythread extends Thread{

privateint type;

public Mythread(inttype,String threadName){

super(threadName);

this.type =type;

}

public void run(){

while(true){

if(type == 0){

ReentrantReadWriteLock.ReadLock readlock = null;

try{

readlock =lock.readLock();

readlock.lock();

System.err.println("to read...." +Thread.currentThread().getName());

try {

Thread.sleep(5000);

}catch (InterruptedException e) {

//TODO Auto-generated catch block

e.printStackTrace();

}

}finally{

   readlock.unlock();

}

}else{

ReentrantReadWriteLock.WriteLockwritelock = null;

try{

writelock=lock.writeLock();

writelock.lock();

System.err.println("to write....." +Thread.currentThread().getName());

try {

Thread.sleep(5000);

}catch (InterruptedException e) {

//TODO Auto-generated catch block

e.printStackTrace();

}


}finally{

writelock.unlock();

}

}

}

}

}

 }

整个demo涉及的代码就这么多,初看也不复杂,但是我预期的执行结果应该是

"to read...." +Thread.currentThread().getName()  //读锁拿到之后,进行打印,sleep到了时间之后进行释放,被写的线程拿到,则打印出

"to write....." +Thread.currentThread().getName() //然后写锁拿到之后,进行该行打印,sleep之后,执行finally的unlock,释放,就该打印出

"to read...." +Thread.currentThread().getName()

...

但实际的执行结果为:

to read....t2

to read....t1

to write.....t3

to write.....t3

to write.....t3

to write.....t3

to write.....t3

...

看起来是writelock的线程拿到lock之后一直没有释放,一直在打印。

对于以上的问题,初步已做的debug为:

System.err.println(reentrantreadwrite.getholdcount);为0,换言之,应该就是已经释放了锁的------------此处不解一


第二,如果在writelock的finally里面随意添加一句system.out.println的语句,,,

则执行结果为:

to read....t2

to read....t1

to write.....t3

before------>java.util.concurrent.locks.ReentrantReadWriteLock$WriteLock@743df815[Locked by thread t3]

to read....t2

after------>java.util.concurrent.locks.ReentrantReadWriteLock$WriteLock@743df815[Unlocked]

to read....t1

to write.....t3

before------>java.util.concurrent.locks.ReentrantReadWriteLock$WriteLock@743df815[Locked by thread t3]to read....t2

to read....t1

after------>java.util.concurrent.locks.ReentrantReadWriteLock$WriteLock@743df815[Unlocked]

to write.....t3

before------>java.util.concurrent.locks.ReentrantReadWriteLock$WriteLock@743df815[Locked by thread t3]to read....t2

after------>java.util.concurrent.locks.ReentrantReadWriteLock$WriteLock@743df815[Unlocked]


to read....t1

此处可以看到,writelock的写锁是被正常释放,打印的信息也是符合预期的~~~


作为一名软件产品测试人员,对于非常底层的开发技术细节相信没有专门的研发系伙伴了解,在此诚挚请求指导,对于以上理解错误,疏漏之处,批评指正,引导~~~


best regards





1 0