文档章节

Java中的线程同步机制

guhanjie
 guhanjie
发布于 2017/04/20 11:12
字数 618
阅读 23
收藏 0

在java中,线程间的同步主要通过两个方面来实现:

  • 锁 —— 用于控制线程级的同步
  • 条件 —— 用于实现线程间的通信和协作

围绕这套线程同步机制,有三个组件:

  • 一个互斥的锁对象(多个线程只有获取到该锁对象才能进入到同步代码块,可以是Object对象监视器锁、或者Lock对象)
  • 一个锁等待队列(waiting_queue,用于容纳等待上面锁对象的线程们)
  • 一个或者多个条件等待队列(condition_queue,某个线程在获得锁后,执行条件等待时进入该队列,在条件满足后从该队列移除,并进入到上面的锁等待队列,等待下一次获取锁的机会)

jdk中的具体实现有2套:

  • Object对象监视器锁、Object#wait()、notify()和notifyAll();
  • Lock锁、条件变量Condition#await()、signal()和signalAll();

他们之间的区别:

  • Object的机制在实际中更常用,而Lock的机制更灵活;
  • Object和Lock的条件等待不太一样:

Object#wait()仅对应一个等待线程集,也即一个监视器锁仅支持一个等待条件;

Lock和Condition可以支持一个锁对象对应多个等待条件,可以有多个条件等待队列。

我手画了一张Object和Lock同步机制的原理实现:

AQS中的锁等待队列和条件队列的实现都是一个由内部类Node节点(代表具体某个线程)组成的双向链表来实现:

* +------+ prev +-----+ +-----+

* head | | <---- | | <---- | | tail

* +------+ +-----+ +-----+

条件队列 Condition Queue

Java中的条件队列可以有效地实现和管理状态依赖性的操作,其有两种实现方式:

  • 内置的条件队列Object#wait()、notify()和notifyAll()
  • 显示的Condition#await()、signal()和signalAll(),但它比前者扩展了功能,如:可实现一个Lock对象对应多个条件队列、可中断、可定时、公平与非公平等待队列唤醒机制。

引用JDK Condition的javadoc:

内置条件队列与内置锁紧密绑定在一起,显示Condition与显示Lock紧密绑定在一起。这是因为管理状态依赖性的机制必须和确保状态一致性的机制关联在一起。

Object#wait()的使用范例:

Lock和Condition的使用范例:

© 著作权归作者所有

上一篇: j.u.c.中的AQS详解
下一篇: Zab vs. Paxos
guhanjie
粉丝 5
博文 3
码字总数 5114
作品 0
上海
程序员
私信 提问
java面试必备之ThreadLocal

按照传统的经验,如果某个对象是非线程安全的,在多线程环境下对象的访问需要采用synchronized进行同步。但是模板类并未采用线程同步机制,因为线程同步会降低系统的并发性能,此外代码同步解...

编程老司机
2018/05/16
0
0
Java中ThreadLocal的设计与使用

ThreadLocal是什么 ThreadLocal是什么呢?其实ThreadLocal并非是一个线程的本地实现版本,它并不是一个Thread,而是thread local variable(线程局部变量)。也许把它命名为ThreadLocalVar更...

DragonRace
2013/11/25
323
0
java类ThreadLocal的理解

ThreadLocal是什么 ThreadLocal是什么呢?其实ThreadLocal并非是一个线程的本地实现版本,它并不是一个Thread,而是thread local variable(线程局部变量)。也许把它命名为ThreadLocalVar更...

保罗的寓言
2011/05/21
574
1
ThreadLocal 基础知识

ThreadLocal是什么 · 早在JDK 1.2的版本中就提供java.lang.ThreadLocal,ThreadLocal为解决多线程程序的并发问题提供了一种新的思路。使用这个工具类可以很简洁地编写出优美的多线程程序。 ...

向阳而生
2015/11/21
209
0
通通透透理解ThreadLocal

通通透透理解ThreadLocal 概述 我们知道Spring通过各种DAO模板类降低了开发者使用各种数据持久技术的难度。这些模板类都是线程安全的,也就是说,多个DAO可以复用同一个模板实例而不会发生冲...

阿秀a
2010/06/15
0
0

没有更多内容

加载失败,请刷新页面

加载更多

OpenStack 简介和几种安装方式总结

OpenStack :是一个由NASA和Rackspace合作研发并发起的,以Apache许可证授权的自由软件和开放源代码项目。项目目标是提供实施简单、可大规模扩展、丰富、标准统一的云计算管理平台。OpenSta...

小海bug
昨天
5
0
DDD(五)

1、引言 之前学习了解了DDD中实体这一概念,那么接下来需要了解的就是值对象、唯一标识。值对象,值就是数字1、2、3,字符串“1”,“2”,“3”,值时对象的特征,对象是一个事物的具体描述...

MrYuZixian
昨天
6
0
数据库中间件MyCat

什么是MyCat? 查看官网的介绍是这样说的 一个彻底开源的,面向企业应用开发的大数据库集群 支持事务、ACID、可以替代MySQL的加强版数据库 一个可以视为MySQL集群的企业级数据库,用来替代昂贵...

沉浮_
昨天
4
0
解决Mac下VSCode打开zsh乱码

1.乱码问题 iTerm2终端使用Zsh,并且配置Zsh主题,该主题主题需要安装字体来支持箭头效果,在iTerm2中设置这个字体,但是VSCode里这个箭头还是显示乱码。 iTerm2展示如下: VSCode展示如下: 2...

HelloDeveloper
昨天
7
0
常用物流快递单号查询接口种类及对接方法

目前快递查询接口有两种方式可以对接,一是和顺丰、圆通、中通、天天、韵达、德邦这些快递公司一一对接接口,二是和快递鸟这样第三方集成接口一次性对接多家常用快递。第一种耗费时间长,但是...

程序的小猿
昨天
8
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部