java 中Lock的使用
2019独角兽企业重金招聘Python工程师标准>>>
ReentrantLock也能够让代码块原子执行,但是比synchronized更加强大,ReentrantLock具有嗅探锁定、多路分支通知等功能。
嗅探锁定:是指获取锁时如果锁已经被其他线程获取到ReentrantLock可以进行指定等待时间获取锁或者
多路分支通知:是指线程发生await时,线程可以选择注册在不同的监视器Condition对象上,在适当的时候可以选择指定的监视器Condition对象上的线程进行signal通知、执行
1、多线程执行同一代码块互斥
import java.util.concurrent.locks.ReentrantLock;class MyService {private ReentrantLock lock = new ReentrantLock();public void method() {try {lock.lock();for (int i = 1; i <= 3; i++) {Thread.sleep(1000);System.out.println("ThreadName=" + Thread.currentThread().getName() + " " + i);}} catch (InterruptedException e) {e.printStackTrace();}finally {lock.unlock();}}
}class MyThread extends Thread {private MyService service;MyThread(MyService service) {this.service = service;}@Overridepublic void run() {service.method();}
}public class Test {public static void main(String[] args) {MyService service = new MyService();MyThread myThread1 = new MyThread(service);MyThread myThread2 = new MyThread(service);myThread1.start();myThread2.start();}
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
结果
ThreadName=Thread-0 1
ThreadName=Thread-0 2
ThreadName=Thread-0 3
ThreadName=Thread-1 1
ThreadName=Thread-1 2
ThreadName=Thread-1 3
2、多线程执行不同代码块互斥
import java.util.concurrent.locks.ReentrantLock;class MyService {private ReentrantLock lock = new ReentrantLock();public void methodA() {lock.lock();try {System.out.println("MethodA begin ThreadName=" + Thread.currentThread().getName());for (int i = 1; i <= 3; i++) {System.out.println("ThreadName=" + Thread.currentThread().getName() + " " + i);Thread.sleep(1000);}System.out.println("MethodA end ThreadName=" + Thread.currentThread().getName());} catch (InterruptedException e) {e.printStackTrace();} finally {lock.unlock();}}public void methodB() {lock.lock();try {System.out.println("MethodB begin ThreadName=" + Thread.currentThread().getName());for (int i = 1; i <= 3; i++) {System.out.println("ThreadName=" + Thread.currentThread().getName() + " " + i);Thread.sleep(1000);}System.out.println("MethodB end ThreadName=" + Thread.currentThread().getName());} catch (InterruptedException e) {e.printStackTrace();} finally {lock.unlock();}}
}class ThreadA extends Thread {private MyService service;ThreadA(MyService service) {this.service = service;}@Overridepublic void run() {service.methodA();}
}class ThreadB extends Thread {private MyService service;ThreadB(MyService service) {this.service = service;}@Overridepublic void run() {service.methodB();}
}public class Test {public static void main(String[] args) {MyService service = new MyService();ThreadA threadA = new ThreadA(service);threadA.setName("A");ThreadB threadB = new ThreadB(service);threadB.setName("B");threadA.start();threadB.start();}
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
- 50
- 51
- 52
- 53
- 54
- 55
- 56
- 57
- 58
- 59
- 60
- 61
- 62
- 63
- 64
- 65
- 66
- 67
- 68
- 69
- 70
- 71
- 72
- 73
- 74
- 75
- 76
- 77
- 78
- 79
- 80
- 81
结果:
MethodA begin ThreadName=A
ThreadName=A 1
ThreadName=A 2
ThreadName=A 3
MethodA end ThreadName=A
MethodB begin ThreadName=B
ThreadName=B 1
ThreadName=B 2
ThreadName=B 3
MethodB end ThreadName=B
3、多路通知
当多线程进入await状态时,利用Condition监视器对不同类型线程通知
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;class MyService {private ReentrantLock lock = new ReentrantLock();private Condition conditionA = lock.newCondition();private Condition conditionB = lock.newCondition();public void methodA() {lock.lock();try {System.out.println("MethodA begin ThreadName=" + Thread.currentThread().getName() + " " + System.currentTimeMillis());conditionA.await();System.out.println("MethodA end ThreadName=" + Thread.currentThread().getName() + " " + System.currentTimeMillis());} catch (InterruptedException e) {e.printStackTrace();} finally {lock.unlock();}}public void methodB() {lock.lock();try {System.out.println("MethodB begin ThreadName=" + Thread.currentThread().getName() + " " + System.currentTimeMillis());conditionB.await();System.out.println("MethodB end ThreadName=" + Thread.currentThread().getName() + " " + System.currentTimeMillis());} catch (InterruptedException e) {e.printStackTrace();} finally {lock.unlock();}}public void signalA() {lock.lock();conditionA.signal();lock.unlock();}public void signalA_All() {lock.lock();conditionA.signalAll();lock.unlock();}public void signalB() {lock.lock();conditionB.signal();lock.unlock();}public void signalB_All() {lock.lock();conditionB.signalAll();lock.unlock();}
}class ThreadA extends Thread {private MyService service;ThreadA(MyService service) {this.service = service;}@Overridepublic void run() {service.methodA();}
}class ThreadB extends Thread {private MyService service;ThreadB(MyService service) {this.service = service;}@Overridepublic void run() {service.methodB();}
}public class Test {public static void main(String[] args) throws InterruptedException {MyService service = new MyService();ThreadA threadA = new ThreadA(service);threadA.setName("A");ThreadB threadB = new ThreadB(service);threadB.setName("B");threadA.start();threadB.start();Thread.sleep(1000);service.signalA();Thread.sleep(1000);service.signalB();// ThreadA[] threadAs = new ThreadA[10];
// for (int i=0;i<5;i++){
// threadAs[i] = new ThreadA(service);
// }
// ThreadB[] threadBs = new ThreadB[10];
// for (int i=0;i<5;i++){
// threadBs[i] = new ThreadB(service);
// }
//
// for (int i=0;i<5;i++){
// threadAs[i].start();
// threadBs[i].start();
// }
//
// Thread.sleep(1000);
// service.signalA_All();
// Thread.sleep(1000);
// service.signalB_All();}
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
- 50
- 51
- 52
- 53
- 54
- 55
- 56
- 57
- 58
- 59
- 60
- 61
- 62
- 63
- 64
- 65
- 66
- 67
- 68
- 69
- 70
- 71
- 72
- 73
- 74
- 75
- 76
- 77
- 78
- 79
- 80
- 81
- 82
- 83
- 84
- 85
- 86
- 87
- 88
- 89
- 90
- 91
- 92
- 93
- 94
- 95
- 96
- 97
- 98
- 99
- 100
- 101
- 102
- 103
- 104
- 105
- 106
- 107
- 108
- 109
- 110
- 111
- 112
- 113
- 114
- 115
- 116
- 117
- 118
- 119
- 120
- 121
- 122
- 123
测试结果1:
MethodA begin ThreadName=A 1476800025028
MethodB begin ThreadName=B 1476800025029
MethodA end ThreadName=A 1476800026028
MethodB end ThreadName=B 1476800027028
修改代码为:
public static void main(String[] args) throws InterruptedException {MyService service = new MyService();
// ThreadA threadA = new ThreadA(service);
// threadA.setName("A");
//
// ThreadB threadB = new ThreadB(service);
// threadB.setName("B");
// threadA.start();
// threadB.start();
//
// Thread.sleep(1000);
// service.signalA();
// Thread.sleep(1000);
// service.signalB();ThreadA[] threadAs = new ThreadA[10];for (int i=0;i<5;i++){threadAs[i] = new ThreadA(service);}ThreadB[] threadBs = new ThreadB[10];for (int i=0;i<5;i++){threadBs[i] = new ThreadB(service);}for (int i=0;i<5;i++){threadAs[i].start();threadBs[i].start();}Thread.sleep(1000);service.signalA_All();Thread.sleep(1000);service.signalB_All();}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
结果为:
MethodA begin ThreadName=Thread-0 1476800227416
MethodB begin ThreadName=Thread-7 1476800227417
MethodB begin ThreadName=Thread-5 1476800227417
MethodA begin ThreadName=Thread-3 1476800227418
MethodA begin ThreadName=Thread-1 1476800227418
MethodA begin ThreadName=Thread-4 1476800227418
MethodB begin ThreadName=Thread-6 1476800227418
MethodA begin ThreadName=Thread-2 1476800227418
MethodB begin ThreadName=Thread-8 1476800227418
MethodB begin ThreadName=Thread-9 1476800227418
MethodA end ThreadName=Thread-0 1476800228419
MethodA end ThreadName=Thread-3 1476800228419
MethodA end ThreadName=Thread-1 1476800228419
MethodA end ThreadName=Thread-4 1476800228420
MethodA end ThreadName=Thread-2 1476800228420
MethodB end ThreadName=Thread-7 1476800229419
MethodB end ThreadName=Thread-5 1476800229419
MethodB end ThreadName=Thread-6 1476800229419
MethodB end ThreadName=Thread-8 1476800229419
MethodB end ThreadName=Thread-9 1476800229419
4、公平所与非公平锁
公平锁是指线程获(getting)取锁的顺序和线程锁定(got)的顺序相同,
Lock的一些方法说明
A) getHoldCount()
获取当前锁定(got)的个数
B)getQueueLength()
获取当前正在等待获取(getting)锁的线程数(Threads)
C)getWaitQueueLength(Condition)
返回等待(await)与此锁定(got)的Condition相关的个数
版权声明:本文为博主原创文章,未经博主允许不得转载。 http://blog.csdn.net/jihaitaowangyi/article/details/52852693
转载于:https://my.oschina.net/u/1177694/blog/1635168
java 中Lock的使用相关推荐
- java 中lock,java中lock获取锁的四种方法
在java接口中会存放着许多方法,方便线程使用时的直接调用.对于lock接口大家都不陌生,我们已经初步对概念进行了理解.那么在获取锁的方法上想必还不是很清楚.下面我们就lock获取锁的四种方法分别进行 ...
- java lock的原理,Java中Lock原理探究
在对于lock锁的使用上,很多人只是掌握了最基础的方法,但是对实现的过程不是很清楚.这里我们对lock锁功能的实现进行分析,以ReentrantLock为例,分析它的锁类型,并对相关的调用方法进行展示 ...
- 一文带你理解Java中Lock的实现原理
转载自 一文带你理解Java中Lock的实现原理 当多个线程需要访问某个公共资源的时候,我们知道需要通过加锁来保证资源的访问不会出问题.java提供了两种方式来加锁,一种是关键字:synchron ...
- java中Lock锁的应用简介
java中Lock锁的应用简介 整体描述 方法介绍 1. void lock() 2. boolean tryLock() 3. boolean tryLock(long timeout, TimeU ...
- java中lock底层实现_Synchronized与Lock的底层实现解析
在JDK1.5之前,我们在编写并发程序的时候无一例外都是使用synchronized来实现线程同步的,而synchronized在JDK1.5之前同步的开销较大效率较低,因此在JDK1.5之后,推出了 ...
- 自旋锁和互斥锁的区别 java中lock Syntronized区别
转载自:http://blog.csdn.net/susidian/article/details/51068858 自旋锁(Spin lock) 自旋锁与互斥锁有点类似,只是自旋锁不会引起调用者睡眠 ...
- java volatile lock_Java并发学习笔记 -- Java中的Lock、volatile、同步关键字
Java并发 一.锁 1. 偏向锁 1. 思想背景 来源:HotSpot的作者经过研究发现,大多数情况下,锁不仅不存在多线程竞争,而且总是由同 一线程多次获得,为了让线程获得锁的代价更低而引入了偏向锁 ...
- Java高并发编程(五):Java中的锁Lock
1. Lock接口 锁是用来控制多个线程访问共享资源的方式,一般来说,一个锁能够防止多个线程同时访问共享资源(但是有些锁可以允许多个线程并发的访问共享资源,比如读写锁).虽然它缺少了(通过synchr ...
- java lock unlock_详解Java中的ReentrantLock锁
ReentrantLock锁 ReentrantLock是Java中常用的锁,属于乐观锁类型,多线程并发情况下.能保证共享数据安全性,线程间有序性 ReentrantLock通过原子操作和阻塞实现锁原 ...
最新文章
- BOS中常用方法和类
- 23,148,855,308,184,500是一个神奇的数字,还是纯粹的机会?
- 活动目录最佳实践分析器
- 非递归遍历二叉树(算法导论第三版第十章10.4-5)
- python fromhex_Python hexstring-list-str之间的转换方法
- spring笔记4-事务管理
- JAVA重要基础之反射
- java中aop和aoc的区别_你喝到的波尔多AOC、AOP红酒是真的吗?
- 生信技能树课程记录笔记(一)20220523
- 华为模拟器eNSP下载与安装(win10系统)
- python word 公式转png图片处理方式
- Centos 环境配置总结(持续更新)
- 流媒体技术介绍(中篇)
- android去掉开机锁屏,android 去掉锁屏
- 初学SQL 注入之常见的几种注入类型
- Win11搜索栏无法使用怎么办?
- X5045看门狗电路
- 【计算机硬件系统设计(华科)——三级时序 CPU「包含中断处理」(Logisim 实现)】
- SIT1040T,芯力特CAN接口芯片,参数描述,完美替代TJA1040
- 解决:Error while adding the mapper ‘interface *** to configuration. Error parsing Mapper XML.