并发编程
并发程序要正确地执行,必须要保证其具备原子性、可见性以及有序性;只要有一个没有被保证,就有可能会导致程序运行不正确
 线程不安全在编译、测试甚至上线使用时,并不一定能发现,因为受到当时的CPU调度顺序,线程个数、指令重排的影响,偶然触发
 
线程安全的定义
比如说一个类,不论通过怎样的调度执行顺序,并且调用处不用对其进行同步操作,其都能表现出正确的行为,则这个类就是线程安全的
 
 
并发编程三个概念
原子性: 一个操作或多个操作要么全部执行且执行过程不被中断,要么不执行
可见性: 多个线程修改同一个共享变量时,一个线程修改后,其他线程能马上获得修改后的值
有序性 : 程序执行的顺序按照代码的先后顺序执行
 
具体实现
 
可以通过 synchronized和Lock实现原子性,因为synchronized和Lock能够保证任一时刻只有一个线程访问该代码块
Java提供了volatile关键字保证可见性
synchronized和lock也可保证可见性,在加锁时其他线程无法访问共享资源
可以通过volatile关键字来保证一定的“有序性”
java提供的解决线程不安全的类:java.util.concurrent.atomic
 
 
 
Atomic类并不使用同步锁,而是采用CAS操作,每次对值进行修改时,先判断其预期值与内存值是否相同,若相同则修改,否则不修改
优点 不加锁,性能较快
缺点 高并发情况下,出错概率越大,长时间CAS不成功,导致CPU消耗过大
注:此种方法是乐观锁,即操作前认为此次操作不会出现竞态,不加锁,只在最后写入主存时进行判断
:ABA问题,当一个值原来是A,被某个线程改成B,又被另个线程改成A,此时CAS操作判断不出已经发生变化,java中使用版本号来解决此问题
 
 
内置锁
java中以synchronized关键字来支持原子性
重入锁
当一个线程已获得锁时,再继续试图获得它已经得到的锁时,这个请求是成功的。
重入锁意味着锁的粒度是线程,而不是每个方法调用
 
重入实现方法:为每个锁关联一个计数器和所有者线程,当计数值为0,即当前没有任何线程获得锁,当线程请求时,JVM记下锁的持有者,计数值置1,当该线程又请求锁时,计数值递增,等其释放,递减到0,锁被释放。
作用 避免死锁

Java并发编程三个性质:原子性、可见性、有序性的更多相关文章

  1. Java并发编程实战 02Java如何解决可见性和有序性问题

    摘要 在上一篇文章当中,讲到了CPU缓存导致可见性.线程切换导致了原子性.编译优化导致了有序性问题.那么这篇文章就先解决其中的可见性和有序性问题,引出了今天的主角:Java内存模型(面试并发的时候会经 ...

  2. 【Java并发编程三】闭锁

    1.什么是闭锁? 闭锁(latch)是一种Synchronizer(Synchronizer:是一个对象,它根据本身的状态调节线程的控制流.常见类型的Synchronizer包括信号量.关卡和闭锁). ...

  3. java并发编程实战《一》可见性、原子性和有序性

    可见性.原子性和有序性问题:并发编程Bug的源头 核心矛盾:CPU.IO.内存三者之间的速度差异. 为了合理利用 CPU 的高性能,平衡这三者的速度差异,计算机体系结构.操作系统.编译程序都做出了贡献 ...

  4. Java 并发编程(三):如何保证共享变量的可见性?

    上一篇,我们谈了谈如何通过同步来保证共享变量的原子性(一个操作或者多个操作要么全部执行并且执行的过程不会被任何因素打断,要么就都不执行),本篇我们来谈一谈如何保证共享变量的可见性(多个线程访问同一个变 ...

  5. Java并发编程(六)原子性与易变性

    原子性 原子是最小单元.不可再分的意思.原子性是指某个操作在获取CPU时间时,要么就给它足够时间,让这个操作执行完,要么就不执行这个操作,执行时不能出现上下文切换(把CPU时间从一个线程分配到另一个线 ...

  6. JAVA并发编程学习笔记------对象的可见性及发布逸出

    一.非原子的64位操作: 当线程在没有同步的情况下读取变量时,可能会得到一个失效值,但至少这个值是由之前某个线程设置的值,而不是一个随机值,这种安全性保证被称为最低安全性.最低安全性适用于绝大多数变量 ...

  7. Java并发编程 (三) 项目准备

    个人博客网:https://wushaopei.github.io/    (你想要这里多有) 一.案例环境初始化 1.环境搭建与准备 Spring Boot 项目,https://start.spr ...

  8. Java并发编程(三):ReentrantLock

    ReentrantLock是可以用来代替synchronized的.ReentrantLock比synchronized更加灵活,功能上面更加丰富,性能方面自synchronized优化后两者性能没有 ...

  9. Java并发编程实战 03互斥锁 解决原子性问题

    文章系列 Java并发编程实战 01并发编程的Bug源头 Java并发编程实战 02Java如何解决可见性和有序性问题 摘要 在上一篇文章02Java如何解决可见性和有序性问题当中,我们解决了可见性和 ...

随机推荐

  1. Linux3.10.0块IO子系统流程(5)-- 为SCSI命令准备聚散列表

    SCSI数据缓冲区组织成聚散列表的形式.Linux内核中表示聚散列表的基本数据结构是scatterlist,虽然名字中有list,但它只对应一个内存缓冲区,聚散列表就是多个scatterlist的组合 ...

  2. java类的高级概念

  3. 使用Java API方式的MapReduce练习

    众所周知,hadoop生态圈的多数组件都是使用java开发的. 那么使用Java API方式实现起来,显得要比其它语言效率更高,更原生态. 前面有一个Hadoop学习笔记02_MapReduce练习 ...

  4. linux command 2

    #修改文件所有权为user group chown user:group file/group 根据:的位置判断是修改所有者还是组 #修改文件读写执行属性 chmod mask file/group ...

  5. 冒泡排序到k趟

    浙大pat题目 将N个整数按从小到大排序的冒泡排序法是这样工作的:从头到尾比较相邻两个元素,如果前面的元素大于其紧随的后面元素,则交换它们.通过一遍扫描,则最后一个元素必定是最大的元素.然后用同样的方 ...

  6. JUnit4测试报错:class not found XXX

     初学java框架,最近用eclipse跟着视频坐淘淘商城这个项目,其中使用了JUnit4做单元测试.当运行测试代码时,项目报错:class not found xxx. 借助了其他大神的博客,论坛等 ...

  7. css自定义checkbox和radio样式

    很常见的问题,也有许多人写过类似的文章,自己写来记录下 css代码如下: #myCheck + label,.myRadio + label{ width:16px; height:16px; bor ...

  8. Java分布式锁

    分布式锁简述 在单机时代,虽然不存在分布式锁,但也会面临资源互斥的情况,只不过在单机的情况下,如果有多个线程要同时访问某个共享资源的时候,我们可以采用线程间加锁的机制,即当某个线程获取到这个资源后,就 ...

  9. 为WebService添加身份验证的两种方法

    方法一:SoapHeader 辅助类:MySoapHeader //SoapHeader 添加引用 using System.Web.Services.Protocols; #region 配置登录标 ...

  10. oracle-ords

    oracle rest data service ORDS Perforce    adv. 一定,必须:必然地pagination    n. 标记页数:页码,分页Online documentat ...