本文内容部分引自《Java多线程编程核心技术》,感谢作者!!!
代码地址:https://github.com/xianzhixianzhixian/thread.git
方法getHoldCount()、getQueueLength()和getWaitQueueLength()用法和区别
1、lock.getHoldCount()作用是查询当前线程保持锁定的个数,也就是调用lock()方法的次数,注意这里“保持锁定“”的意思是,当前正在持有锁的线程的个数。
2、lock.getQueueLength()的作用是返回正在等待获取此锁定的线程的估计数。比如有5个线程,1个线程首先执行await()方法,那么在调用getQueueLength()方法后返回值是4,说明有4个线程同时在等待lock的释放。注意这里“等待获取此锁”的意思是当前处于lock状态且未持有锁的线程的个数。
3、lock.getWaitQueueLength(Condition condition)方法的作用是返回等待与此锁定相关的给定条件Condition的线程估计数。比如说有5个线程,每个线程都执行了同一个condition对象的await()方法,则调用getWaitQueueLength(Condition condition)方法的返回值是5。特别注意:这里返回值统计的是调用同一个condtion的await()方法且处于await状态的线程个数。
代码示例
ServiceGetHoldCount.java
/**
* getHoldCount()的使用示例
* lock.getHoldCount()作用是查询当前线程保持锁定的个数,也就是调用lock()方法的次数
*
* 注意这里保持锁定的意思是,当前正在持有锁的线程的个数
* @author: xianzhixianzhixian
* @date: 2019-01-15 21:15
*/
public class ServiceGetHoldCount {
public ReentrantLock lock = new ReentrantLock();
public void serviceGetHoldCount1(){
try {
lock.lock();
System.out.println("serviceGetHoldCount1 getHoldCount()="
+lock.getHoldCount());
serviceGetHoldCount2();
} catch (Exception e) {
e.printStackTrace();
} finally {
lock.unlock();
}
}
public void serviceGetHoldCount2(){
try {
lock.lock();
System.out.println("serviceGetHoldCount2 getHoldCount()="
+lock.getHoldCount());
} catch (Exception e) {
e.printStackTrace();
} finally {
lock.unlock();
}
}
}
ServiceGetQueueLength.java
/**
* getQueueLength()的使用示例
* lock.getQueueLength()的作用是返回正在等待获取此锁定的线程的估计数
* 比如有5个线程,1个线程首先执行await()方法,那么在调用getQueueLength()方法后返回值是4,说明有4个线程同时在等待lock的释放
*
* 注意这里等待获取此锁的意思是当前处于lock状态且未持有锁的线程的个数
* @author: xianzhixianzhixian
* @date: 2019-01-15 21:24
*/
public class ServiceGetQueueLength {
public ReentrantLock lock = new ReentrantLock();
public void serviceGetQueueLength(){
try {
lock.lock();
System.out.println("ThreadName="+Thread.currentThread().getName()
+"进入方法");
Thread.sleep(Integer.MAX_VALUE);
} catch (Exception e) {
e.printStackTrace();
} finally {
lock.unlock();
}
}
}
ServiceGetWaitQueueLength.java
/**
* getWaitQueueLength(Condition condition)的使用示例
* lock.getWaitQueueLength(Condition condition)方法的作用是返回等待与此锁定相关的给定条件Condition的线程估计数
* 比如说有5个线程,每个线程都执行了同一个condition对象的await()方法,则调用getWaitQueueLength(Condition condition)
* 方法的返回值是5
*
* 特别注意:这里返回值统计的是调用同一个condtion的await()方法且处于await状态的线程个数
* @author: xianzhixianzhixian
* @date: 2019-01-15 21:34
*/
public class ServiceGetWaitQueueLength {
private ReentrantLock lock = new ReentrantLock();
private Condition condition = lock.newCondition();
public void awaitMethod(){
try {
lock.lock();
condition.await();
} catch (Exception e) {
e.printStackTrace();
} finally {
lock.unlock();
}
}
public void notifyMethod(){
try {
lock.lock();
System.out.println("有"+lock.getWaitQueueLength(condition)
+"个线程正在等待condition");
condition.signal();
} catch (Exception e) {
e.printStackTrace();
} finally {
lock.unlock();
}
}
}
Run.java
/**
* getHoldCount()、getQueueLength()和getWaitQueueLength()区别
* @author: xianzhixianzhixian
* @date: 2019-01-15 21:20
*/
public class Run {
public static void main(String[] args) throws Exception {
ServiceGetHoldCount serviceGetHoldCount = new ServiceGetHoldCount();
serviceGetHoldCount.serviceGetHoldCount1();
System.out.println("serviceGetHoldCount.lock.getQueueLength()"+serviceGetHoldCount.lock.getQueueLength());
final ServiceGetQueueLength serviceGetQueueLength = new ServiceGetQueueLength();
Runnable runnableGetQueueLength = new Runnable() {
@Override
public void run() {
serviceGetQueueLength.serviceGetQueueLength();
}
};
Thread[] threadArrayGetQueueLength = new Thread[10];
for (int i = 0; i < 10; i++) {
threadArrayGetQueueLength[i] = new Thread(runnableGetQueueLength);
}
for (int i = 0; i < 10; i++) {
threadArrayGetQueueLength[i].start();
}
Thread.sleep(2000);
System.out.println("有线程数:"+ serviceGetQueueLength.lock.getQueueLength()+"在等待获取锁!");
final ServiceGetWaitQueueLength serviceGetWaitQueueLength = new ServiceGetWaitQueueLength();
Runnable runnableGetWaitQueueLength = new Runnable() {
@Override
public void run() {
serviceGetWaitQueueLength.awaitMethod();
}
};
Thread[] threadArrayGetWaitQueueLength = new Thread[10];
for (int i = 0; i < 10; i++) {
threadArrayGetWaitQueueLength[i] = new Thread(runnableGetWaitQueueLength);
}
for (int i = 0; i < 10; i++) {
threadArrayGetWaitQueueLength[i].start();
//serviceGetWaitQueueLength.notifyMethod();
}
Thread.sleep(2000);
serviceGetWaitQueueLength.notifyMethod(); //只唤醒一个处于await状态的线程
}
}
运行结果:getHoldCount()的返回值为2,因为有两个线程获得了锁;getQueueLength()的返回值为9,因为此时有一个线程获得了锁并且一直处于sleep状态,而其它九个线程处于等待锁被释放的状态;getWaitQueueLength(Condition condition)的返回值为10,因为所有10个线程都调用了condition.await()方法且都处于await状态。