深入理解JAVA虚拟机阅读笔记6——线程安全与锁优化
线程安全:如果一个对象可以安全的被多个线程同时使用,那它就是线程安全的。
一、Java中的线程安全
1.不可变
不可变的对象一定是线程安全的。String、枚举类型、java.lang.Number的部分子类如Long和Double等数值包装类型,BigInteger和BigDecimal等大数据类型。
AtomicInteger和AtomicLong并非是不可变的。
2.绝对线程安全
如Vector类是线程安全的,但是如果多个线程同时对Vector数据进行增加或者减少,那么Vector线程不是绝对线程安全的。
3.相对线程安全
单独操作是线程安全的,连续操作需考虑同步问题。
4. 线程兼容
5. 线程独立
二、线程安全的实现方法
1. 互斥同步(阻塞同步)
基本概念:
同步是指在多个线程并发访问共享数据时,保证共享数据在同一个时刻只被一个(或者一些)线程使用。
互斥是实现同步的一种手段,临界区(Critical Section)、互斥量(Mutex)和信号量(Semaphore)都是互斥实现方式。
互斥是因,同步是果;互斥是方法,同步是目的。
实现方法:
synchronized对同一线程可重入,对不同线程阻塞。因为java线程是使用操作系统的原生线程实现的,因此synchronized是一个重量级操作。
ReentrantLock重入锁。
- 等待可中断
- 可实现公平锁
- 锁可以绑定多个条件
2. 非阻塞同步
互斥同步是一种悲观锁,总是假定不去同步肯定会出问题。
非阻塞同步是一种乐观锁,是基于冲突检测的方法,先进行操作,如果产生了冲突,重试。
产生“ABA”问题。
3. 无同步问题
可冲入代码
线程本地存储
三、锁优化
1. 自旋锁和自适应自旋锁
因为线程切换是一个重量级的操作,所以对于多处理器来说。如果线程被阻塞,那么会先执行一个忙循环(自旋操作)。
自适应自旋转锁:自旋的次数会根据 自旋操作是否成功获取过锁来 自适应调节下次自旋次数。
2. 锁消除
锁消除是指虚拟机即时编译器在运行时,对要求同步的代码,检测到不可能存在共享数据竞争的锁进行消除。
3. 锁粗化
对一系列连续操作都是同一个对象反复加锁解锁的情况,将锁范围扩大到整个操作系列以外。
4. 轻量级锁
在无竞争的情况下使用CAS操作去消除同步使用的互斥量。
5. 偏向锁
在无竞争的情况下把整个同步都消除掉。
深入理解JAVA虚拟机阅读笔记6——线程安全与锁优化的更多相关文章
- 深入理解java虚拟机-第13章-线程安全与锁优化
第十三章 线程安全与锁优化 线程安全 java语言中的线程安全 1 不可变.Immutable 的对象一定是线程安全的 2 绝对线程安全 一个类要达到不管运行时环境如何,调用者都不需要额外的同步措施, ...
- 深入理解java虚拟机(7)---线程安全 & 锁优化
关于线程安全的话题,足可以使用一本书来讲解这些东西.<Java Concurrency in Practice> 就是讲解这些的,在这里 主要还是分析JVM中关于线程安全这块的内容. 1. ...
- 深入理解Java虚拟机读书笔记9----线程完全与锁优化
九 线程完全与锁优化 1 Java语言中的线程完全 ---线程安全:当多个线程访问一个对象时,如果不用考虑这些线程在运行时环境下的调度和交替执行,也不需要进行额外的同步,或者在调用 ...
- 深入理解Java虚拟机--阅读笔记一
Java内存区域 一.java运行时数据区域 1. 程序计数器:程序计数器占据的内存空间较小,是当前运行线程执行的字节码的计数:分支.循环.跳转.异常处理.线程恢复等都要依赖技术器来对执行的字节码进行 ...
- 深入理解JAVA虚拟机阅读笔记5——Java内存模型与线程
Java内存模型是定义线程共享的变量的访问规则(实例字段.静态字段和构成数组对象的元素),但不包括线程私有的局部变量和方法参数. 1.主内存与工作内存 Java内存模型规定,所有的变量都必须存储在主内 ...
- 深入理解Java 虚拟机阅读笔记(一)
1.程序计数器- 占用空间:较小 作用:字节码行号指示器 作用详情:指示指令执行,如(字节码的执行,分支,循环,跳转,异常处理,线程恢复) 特点:线程私有(每个计数器独立计算,上下文相互独立). 2. ...
- 深入理解Java虚拟机--阅读笔记二
垃圾收集器与内存分配策略 一.判断对象是否已死 1.垃圾收集器在对堆进行回收前,要先判断对象是否已死.而判断的算法有引用计数算法和可达性分析算法: 2.引用计数算法是给对象添加引用计数器,有地方引用就 ...
- 深入理解JAVA虚拟机阅读笔记1——JAVA内存区域
一.Java内存区域 1.程序计数器 线程私有. 当前线程所执行的字节码的行号指示器.由于JAVA是多线程的,因此每个线程都独立的程序计数器. 异常:没有规定任何OutOfMemeryError情况的 ...
- 深入理解java虚拟机阅读笔记(1)运行时数据区域
java虚拟机所管理的内存区域主要分为方法区.堆:虚拟机栈.本地方法栈.程序计数器,如图: 1.程序计数器是当前线程所执行的字节码行号指示器,用以记录当前指令执行的位置.程序计数器是线程私有的,每个线 ...
随机推荐
- UVA10559 Blocks
玄学东西,毒瘤状态,死也想不出 设f[l][r][i]表示[l,r]区间,右边再加上i个颜色和r颜色相同的块,消掉这些的最大收益 两种转移方式: 把r和后面i个一起销毁,\(f[l][r-1][0]+ ...
- monkey测试入门3
本文要感谢一起战斗过的点时小伙伴,程童鞋 打开开始 输入cmd 看到它的目录地址 然后把adb压缩包解压到该地址 插入数据线 打开手机设置打开开发者选项 打开USB调试 右键点击我的电脑 选择管理 左 ...
- 简单的redis工具类
import java.util.Arrays; import java.util.List;import java.util.Set; import org.apache.commons.lang. ...
- 聊聊前段插件之Datatables
在web开发过程中表格数据展示是一个很常见的功能,而且用户对其要求也比较高,性能.易用性等.今天我推荐一款利器给大家——Datatables:Datatables中文网. 一.介绍 Datatable ...
- Halcon四 双目视觉的标定
原文作者写的一系列博客,挺不错的学习halcon:http://blog.sina.com.cn/s/blog_442bfe0e0100yjtn.html 1.get_image_pointer1(I ...
- RabbitMQ入门:主题路由器(Topic Exchange)
上一篇博文中,我们使用direct exchange 代替了fanout exchange,这次我们来看下topic exchange. 一.Topic Exchange介绍 topic exchan ...
- Web APi 入门例子
http://www.cnblogs.com/guyun/p/4589115.html#what
- 关于MySql数据库主键及索引的区别
一.什么是索引?索引用来快速地寻找那些具有特定值的记录,所有MySQL索引都以B-树的形式保存.如果没有索引,执行查询时MySQL必须从第一个记录开始扫描整个表的所有记录,直至找到符合要求的记录.表里 ...
- asp.net core如何修改程序监听的端口
asp.net core 默认监听的5000和5001端口,要修改为其他端口有几种方法. 1.硬编码.优点是直观,缺点是每次修改端口都得重新编译程序. public class Program { p ...
- [java] jar file
查看 .jar 内的文件 jar tf jarfile.jar maven 项目中, java 读取目标文件 运行 mvn package 打包项目是, src/main/resources 下的文件 ...