并发编程之synchronized关键字
synchronized关键字
synchronized关键字最主要的三种使用方式的总结
1.修饰实例方法,作用于当前对象实例加锁,进入同步代码块前要获得当前对象实例的锁
2.修饰静态方法,作用于当前类对象加锁,进入同步代码块前要获得当前类对象的锁。也就是给当前类加锁,会作用于类的所有对象实例,因为静态成员不属于任何一个实例
对象,是类成员(static表明这是该类的一个静态资源,不管new了多少个对象,只有这一份),如果一个线程A调用一个实例对象的非静态synchronized方法,而线程B调用
这个实例对象所属类的静态synchronized方法,是允许的,不会发生互斥现象。因为访问静态的synchronized方法占用的锁是当前类的锁,访问非静态的synchronized方法
占用的锁是当前实例对象的锁。
3.修饰代码块,指定加锁对象,对给定对象加锁,进入同步代码块前要获得给定对象的锁。和synchronized方法一样,synchronized(this)代码块也是锁定当前对象的。
synchronized关键字加到static方法和synchronized(class)代码块上都是都是给class类上锁。再提一下,synchronized关键字非静态方法上是给当前对象实例加锁,另外需要
注意的是,尽量不要使用synchronized(String a)因为JVM中字符串常量池具有缓冲功能。
双重校验锁实现对象单例
public class Singleton {
private volatile static Singleton singleton;
private Singleton(){}
public static Singleton getSingleton(){
if (singleton==null){
synchronized (Singleton.class){
if (singleton==null){
singleton = new Singleton();
}
}
}
return singleton;
}
}
需要注意的是singleton对象使用volatile关键字修饰原因如下:
singleton = new Singleton(); 这段代码其实分为三步执行,第一步为singleton分配内存空间,第二步初始化singleton,第三部将singleton指向分配的内存地址,但是由于
JVM具有指令重排的特征,执行顺序有可能变成第一步->第三步->第二步,此指令重排在单线程环境下没有问题,但是在多线程环境下会导致某个线程获得还没有初始化
的实例。例如线程1执行了第一步和第三步,此时线程2调用getSingleton()方法发现singleton并不为空,因此返回singleton,但此时singleton还未初始化。使用volatile
关键字可以禁止JVM的指令重排,保证在多线程环境下正常运行。
synchronized关键字和volatile关键字的区别
把变量声明为volatile,当一个线程在工作内存中修改该变量的值之后会立即将值同步到主内存,同时使其他线程的工作内存缓存的原始值无效,另一个线程需要使用
这个变量时,需要重新从主内存读取该变量值到自己的工作内存,保证了变量的可见性,还有一个作用是防止指令重排序。
区别有以下几点:
1.volatile关键字是线程同步的轻量级实现,所以volatile关键字的性能肯定要比synchronized关键字要好,但是volatile关键字只能用于变量,而synchronized关键字可以
修饰方法和代码块。在JDK1.6之后进行了获得锁和释放锁带来的性能消耗的优化,相对来说synchronized关键字使用场景较多一点
2.多线程访问volatile关键字不会发生阻塞,synchronized可能会发生阻塞
3.volatile关键字能保证数据的可见性,但不能保证数据的原子性,synchronized关键字两者都能保证
4.volatile关键字主要用于解决变量在多个线程之间的可见性,synchronized关键字解决的是多个线程之间访问资源的同步性
并发编程之synchronized关键字的更多相关文章
- Java并发编程之synchronized关键字
整理一下synchronized关键字相关的知识点. 在多线程并发编程中synchronized扮演着相当重要的角色,synchronized关键字是用来控制线程同步的,可以保证在同一个时刻,只有一个 ...
- Java 多线程并发编程之 Synchronized 关键字
synchronized 关键字解析 同步锁依赖于对象,每个对象都有一个同步锁. 现有一成员变量 Test,当线程 A 调用 Test 的 synchronized 方法,线程 A 获得 Test 的 ...
- 高并发编程之synchronized
一.什么是线程? 线程,有时被称为轻量级进程(Lightweight Process,LWP),是程序执行流的最小单元.一个标准的线程由线程ID,当前指令指针(PC),寄存器集合和堆栈组成.另外,线程 ...
- Java并发编程之volatile关键字解析
一内存模型的相关概念 二并发编程中的三个概念 三Java内存模型 四深入剖析volatile关键字 五使用volatile关键字的场景 volatile这个关键字可能很多朋友都听说过,或许也都用过.在 ...
- 并发编程之synchronized锁(一)
一.设计同步器的意义 多线程编程中,有可能会出现多个线程同时访问同一个共享.可变资源的情况,这个资源我们称之其为临界资源:这种资源可能是:对象.变量.文件等. 共享:资源可以由多个线程同时访问 可变: ...
- Java并发编程之volatile关键字
大概是因为项目.业务的原因,工作上几乎还没有使用过多线程相关的功能,相关知识差不多都忘了,所以最近补一下基础. volatile用来修饰共享变量,volatile变量具有 synchronized 的 ...
- Java 并发编程之volatile关键字解析
摘录 1. 计算机在执行程序时,每条指令都是在CPU中执行的,而执行指令过程中,势必涉及到数据的读取和写入.由于程序运行过程中的临时数据是存放在主存(物理内存)当中的,这时就存在一个问题,由于CPU执 ...
- Java并发编程之synchronized
在Java编程中,为了保证线程安全,有3种不同的思路1.互斥同步:包括synchronized和lock等. 2.非阻塞同步:如AtomicInteger的increaseAndGet()方法等. 3 ...
- 并发编程之synchronized(二)------jvm对synchronized的优化
一.锁的粗化 看如下代码 public class Test { StringBuffer stb = new StringBuffer(); public void test1(){ //jvm的优 ...
随机推荐
- mysql的基础用法,水一下
#和上一篇是一起的,上一篇就是为这个做insert <blockquote>/*思考题*/ create database spj; use spj;create table s( sno ...
- hsdf -- 6.21 -- day6
差点忘写总结…… 这么快就到day6了啊 感觉前面写的总结都是苟屁,跟没有有什么区别…… 今天认真总结一下 最大的失误就是全程肝a题,最后还挂了…… 感觉今天方向偏了,由进行一次测试到仅仅是想要尽可能 ...
- python中使用if __name__ == '__main__':
引子 在python中,假设在一个test1.py的模块中定义了一个foo函数,然后调用函数foo进行测试的时候会产生一个内存空间.当你把这个模块导入到test2.py模块中,接下来如果在test2. ...
- remove-weknow-ac from mac chrome
refer:https://macreports.com/how-to-remove-weknow-ac-malware-macos/ 1-Remove the weknow.ac profile. ...
- redis 批量删除 keys
#!/bin/bash redis_list=("192.168.252.174:7000" "192.168.252.174:7001" "192. ...
- centos7配置iscsi
什么是ISCSI iscsi--internet small computer system interface互联小型计算机系统接口,将数据包封装在TCP/IP协议中传输,使用普通网线和网络设备即可 ...
- Anaconda下安装OpenCV
安装命令:conda install -c https://conda.binstar.org/menpo opencvwin10+Anaconda3+python3.5.2,最终cv版本为3.3.1 ...
- bpmn-js起步
https://blog.csdn.net/u013253924/article/details/85784002 通过本文逐步熟悉bpmn-js. 快速介绍: bpmn.js是一个BPMN2.0渲染 ...
- jmeter问题
1.使用jmeter传入json参数报错 具体场景:使用python+request执行接口测试,正常:把python的参数直接复制,使用jmeter执行接口测试,提示json格式错误. {...,& ...
- [UE4]让Spline具象化
接上一个实例 一.在TestSpline蓝图,切换到蓝图构造函数Constrction Script事件中,添加如下代码: 二.别忘记个Add Spline Mesh Component设置Stati ...