java程会释放锁join_关于join() 是否会释放锁的一些思考
# 首先从一个很有意思的问题开始:
- 问 : Thread 的join() 方法是否会释放锁?
- 答: 会!
# 如果一切到这里就结束了,那可能也就没有这篇小记了,但是我的脑子却冒出了一些奇怪的想法:
- 释放哪个对象的锁呢?
- 难道是释放父线程所持有的所有对象的锁?
-- 其实如果看了源码,很容易明白释放的是运行(这个地方可能有些歧义,但是我也不知道怎么说最好)join()方法的那个线程对象的锁,不过这些都是后话,我们且往下看;
# 然后我就写了代码来验证一下我的猜想, 代码如下:
public classQQ {public static voidmain(String[] args) {
Object oo= newObject();
Thread thread1= new MyThread("thread1 -- ", oo);
thread1.start();synchronized(oo) {for (int i = 0; i < 100; i++) {if (i == 20) {try{
thread1.join();
}catch(InterruptedException e) {
e.printStackTrace();
}
}
System.out.println(Thread.currentThread().getName()+ " -- " +i);
}
}
}
}class MyThread extendsThread {privateString name;privateObject oo;publicMyThread(String name, Object oo) {this.name =name;this.oo =oo;
}
@Overridepublic voidrun() {synchronized(oo) {for (int i = 0; i < 100; i++) {
System.out.println(name+i);
}
}
}
}
- 运行一下,输出到 main -- 19 的时候,卡住了。
- 接下来我们来寻找卡住的原因;
-- 先使用jps找到出问题程序的进程号
-- jstack pid 来查看线程堆栈,结果如下图
"Thread-1" #14 prio=5 os_prio=0 tid=0x0000000018fa9000 nid=0x3f80 waiting for monitor entry [0x0000000019b0f000]
java.lang.Thread.State: BLOCKED (on object monitor)- waiting to lock <0x00000000d8a06298>(a java.lang.Object)"main" #1 prio=5 os_prio=0 tid=0x000000000228e800 nid=0x3d6c in Object.wait() [0x00000000028af000]
java.lang.Thread.State: WAITING (on object monitor)- locked <0x00000000d8a06298> (a java.lang.Object)
-- 上图中我删掉了很多东西,只留下了一些关键的部分;首先我们看到 Thread-1 和 main 都在 waiting 状态,然后再注意到 Thread-1 在等待锁 <0x00000000d8a06298>,
但是main持有锁<0x00000000d8a06298>, 这又是什么情况呢? 难道 main 没有释放锁?
- 这时候我们就回到了最初的问题,到底join()的时候释放的是谁的锁,通过查看join()方法的源码,很容易看到,其实调用的是 this.wait(),也就是说释放的是Thread-1 这个对象的锁
# 接着我们来用下面的代码证实一下我们得出的结论
public classQQ {public static voidmain(String[] args) {
Object oo= newObject();
Thread thread1= new MyThread("thread1 -- ", oo);
thread1.start();synchronized(thread1) {for (int i = 0; i < 100; i++) {if (i == 20) {try{
thread1.join();
}catch(InterruptedException e) {
e.printStackTrace();
}
}
System.out.println(Thread.currentThread().getName()+ " -- " +i);
}
}
}
}class MyThread extendsThread {privateString name;privateObject oo;publicMyThread(String name, Object oo) {this.name =name;this.oo =oo;
}
@Overridepublic voidrun() {synchronized (this) {for (int i = 0; i < 100; i++) {
System.out.println(name+i);
}
}
}
}
- 很容易验证我们的猜想和理解是正确的
# 再接下来我们看一下如果调用wait() 方法,应该是怎么个情况呢;
public classQQ {public static voidmain(String[] args) {
Object oo= newObject();
Thread thread1= new MyThread("thread1 -- ", oo);
thread1.start();synchronized(oo) {for (int i = 0; i < 100; i++) {if (i == 20) {try{
oo.wait();
}catch(InterruptedException e) {
e.printStackTrace();
}
}
System.out.println(Thread.currentThread().getName()+ " -- " +i);
}
}
}
}class MyThread extendsThread {privateString name;privateObject oo;publicMyThread(String name, Object oo) {this.name =name;this.oo =oo;
}
@Overridepublic voidrun() {synchronized(oo) {for (int i = 0; i < 100; i++) {
System.out.println(name+i);
}
oo.notifyAll();
}
}
}
- 乍一看,和调用join() 方法的现象一样;
- 嗯。。。有点意思了。。。
# 最后补充一点:jstack中的Thread-1 和 我们自己定义的 thread1 是不一样的,如果想要在jstack中显示我们自己定义的线程名, 则需要调用Thread的setName()方法
java程会释放锁join_关于join() 是否会释放锁的一些思考相关推荐
- java线程join方法会释放锁吗
java线程join方法会释放锁吗,虽然join底层使用wait,wait是释放锁的 wait()和join()的调用方的区别: object.wait()和thread.join() join()的 ...
- java wait 释放锁_JAVA锁之wait,notify(wait会释放锁,notify仅仅只是通知,不释放锁)...
wait是指在一个已经进入了同步锁的线程内,让自己暂时让出同步锁,以便其他正在等待此锁的线程可以得到同步锁并运行,只有其他线程调用了notify方法(notify并不释放锁,只是告诉调用过wait方法 ...
- java 并发锁_Java并发教程–锁定:内在锁
java 并发锁 在之前的文章中,我们回顾了在不同线程之间共享数据的一些主要风险(例如原子性和可见性 )以及如何设计类以安全地共享( 线程安全的设计 ). 但是,在许多情况下,我们将需要共享可变数据, ...
- Java核心(三)并发中的线程同步与锁
2019独角兽企业重金招聘Python工程师标准>>> 乐观锁.悲观锁.公平锁.自旋锁.偏向锁.轻量级锁.重量级锁.锁膨胀...难理解?不存的!来,话不多说,带你飙车. 上一篇介绍了 ...
- java 锁_Java之线程并发的各种锁、锁、锁
因为两周没更新了... 也不是懒,这两周确实有些忙,赶项目进度赶的不亦乐乎... 终于赶在工期前,可以进入内测了,我也有了些时间,可以更新啦... 线程并发锁是很常见的问题,而且在Java中锁的类型. ...
- java中锁的基本原理和升级:偏向锁、轻量级锁、重量级锁
目录 由一个问题引发的思考 多线程对于共享变量访问带来的安全性问题 线程安全性 思考如何保证线程并行的数据安全性 synchronized 的基本认识 synchronized 的基本语法 synch ...
- java的尝试性问题_Java并发编程实战 03互斥锁 解决原子性问题
文章系列 摘要 在上一篇文章02Java如何解决可见性和有序性问题当中,我们解决了可见性和有序性的问题,那么还有一个原子性问题咱们还没解决.在第一篇文章01并发编程的Bug源头当中,讲到了把一个或者多 ...
- java多线程中的死锁、活锁、饥饿、无锁都是什么鬼?
转载自 java多线程中的死锁.活锁.饥饿.无锁都是什么鬼? 死锁.活锁.饥饿是关于多线程是否活跃出现的运行阻塞障碍问题,如果线程出现了这三种情况,即线程不再活跃,不能再正常地执行下去了. 死锁 死锁 ...
- java如何保证redis设置过期时间的原子性_分布式锁用 Redis 还是 Zookeeper
在讨论这个问题之前,我们先来看一个业务场景: 系统A是一个电商系统,目前是一台机器部署,系统中有一个用户下订单的接口,但是用户下订单之前一定要去检查一下库存,确保库存足够了才会给用户下单. 由于系统有 ...
最新文章
- 琥珀项目:较小的,面向生产力的Java语言功能
- php 单引号 数据库,关于php:如何在写入Mysql数据库时处理撇号’单引号
- python安装成功的图标_安装Python
- java编程算法出现在窗口_Java实现轨迹压缩算法开放窗口代码编程实例分享
- 【免费下载】2021年5月热门报告盘点下载
- php @file_exists 前面加at是什么意思,PHP file_exists()函数前加反斜杠“\”是什么意思?...
- 麦肯锡:全球调研14个行业、160个案例、3000名高管,AI应用到哪一步了?
- mysql lvs+keepalived+mha_MHA+Lvs+Keepalived实现MySQL的高可用及读负载均衡_2(MySQL)
- html5给文字添加拼音,word怎么为文字添加拼音
- 期货市场间竞争的比较优势分析
- 怎么快速解决dns被劫持问题?
- python 爬取有道词典翻译
- npm ERR! This is probably not a problem with npm. There is likely additional logging output above.
- kubeadm工作原理-kubeadm init原理分析-kubeadm join原理分析
- Django请求和响应对象
- Smmu硬件寄存器—V2
- CSP-J CSP-S 初赛模拟题
- jenkins构建失败后将信息发送到企业微信
- Metasploit用法大全
- 宝塔linux如何防护,使用宝塔面板的CC***防护策略
热门文章
- java 构建者模式_Java方法中的参数太多,第3部分:构建器模式
- Java 11将包含更多功能
- primefaces_轻量级Web应用程序:PrimeFaces(JSF)+ Guice + MyBatis(第1部分)
- 将Jython嵌入到您的Java代码库中
- pl/postgresql_PostgreSQL PL / java简介
- 针对新手的Java EE7和Maven项目–第8部分
- EE JSP:使用JSTL标记库生成动态内容
- 扩展Spring Batch –步骤分区
- Spring:使基于Java的配置更加优雅
- 很少使用“ ControlFlowException”