前言 楼主这个标题其实有一种作死的味道,为什么呢,这三个东西其实可以分开为三篇文章来写,但是,楼主认为这三个东西又都是高度相关的,应当在一个知识点中.在一次学习中去理解这些东西.才能更好的理解 Java 内存模型和 volatile 关键字还有 HB 原则. 楼主今天就尝试着在一篇文章中讲述这三个问题,最后总结. 讲并发知识前必须复习的硬件知识. Java 内存模型到底是什么玩意? Java 内存模型定义了哪些东西? Java内存模型引出的 Happen-Before 原则是什么? Happen…
在介绍Java内存模型之前,先来了解一下为什么要有内存模型,以及内存模型是什么.然后我们基于对内存模型的了解,学习Java内存模型以及并发编程的三大特性. 为什么要有内存模型 在计算机中,所有的运算操作都是由CPU的寄存器来完成的,CPU指令的执行需要涉及到数据的读写操作,而CPU只能访问主存中的数据.随着技术的发展,CPU的执行速度越来越快,而内存的访问速度没有太大的变化,导致CU每次操作主存都要等待很长的时间.于是就有了在CPU与主存之间添加缓存的设计. 内存模型:CPU Cache模型 目…
一.图例 0.两个概念 Heap(堆):运行时的数据区,由垃圾回收负责,运行时分配内存(所以慢),对象存放在堆上 如果两个线程,同时调用同一个变量,怎两个线程都拥有,该对象的私有拷贝 (可以看一下,ThreadLocal:   引用注明出处,https://www.cnblogs.com/xiaonantianmen/p/9151481.html) Stack(栈):存放一些引用变量 二.多cpu情况 0.JVM与物理内存之间的通信. 2.线程之间的通信必须通过主内存(此处则是要考虑synchr…
本文主要是学习Java内存模型的笔记以及加上自己的一些案例分享,如有错误之处请指出. 一 Java内存模型的基础 1.并发编程模型的两个问题 在并发编程中,需要了解并会处理这两个关键问题: 1.1.线程之间如何通信? 通信是指线程之间以何种机制来交换信息.在命令式编程中,线程之间的通信机制有两种:共享内存和消息传递. a) 在共享内存的并发模型里,线程之间共享程序的公共状态,通过写-读内存中的公共状态进行隐式通信.(重点) b) 在消息传递的并发模型里,线程之间没有公共状态,线程之间必须通过发送…
<深入了解java虚拟机>高效并发读书笔记--Java内存模型,线程,线程安全 与锁优化 本文主要参考<深入了解java虚拟机>高效并发章节 关于锁升级,偏向锁,轻量级锁参考<Java并发编程的艺术> 关于线程安全和线程安全的程度参考了<Java并发编程实战> 图片参考https://www.processon.com/u/5dee0443e4b093b9f775065c#pc 一丶Java内存模型 1.概述 多任务处理已经是操作系统的必备技能,计算机被要求…
个人理解: 1.并发编程分为三个核心:分工.同步.互斥 2.CPU.内存.I/O存在速度差异问题. 3.线程切换导致原子性问题.编译优化导致有序性问题.缓存导致可见性问题. 4.Java内存模型规范了JVM如何提供按需禁用缓存和编译优化的方法.这些方法包括:volatile.synchronized和final是三个关键字以及六项Happen-Before原则. 5.volatile:禁用CPU缓存,直接从内存中读取数据. 6.happen-before:前面一个操作的结果对于后续的操作是可见的…
Java内存模型 1 基本概念 程序:代码,完成某一个任务的代码序列(静态概念) 进程:程序在某些数据上的一次运行(动态) 线程:一个进程有一个或多个线程组成(占有资源的独立单元) 2 JVM与线程 jvm启动时期 类被调用: JVM线程启动--> 启动其他线程(main) 3 jvm内存区域(运行时数据区) Java虚拟机会在程序运行时将内存自动划分为以上几个区域,每个区域都有其作用及创建和销毁时机. 方法区:(共享区域)存储已被加载的类信息.常量.静态变量(static).即时编译器编译后的…
前言 解决并发编程中的可见性和有序性问题最直接的方法就是禁用CPU缓存和编译器的优化.但是,禁用这两者又会影响程序性能.于是我们要做的是按需禁用CPU缓存和编译器的优化. 如何按需禁用CPU缓存和编译器的优化就需要提到Java内存模型.Java内存模型是一个复杂的规范.其中最为重要的便是Happens-Before规则.下面我们先介绍如何利用Happens-Before规则解决可见性和有序性问题,然后我们再扩展简单介绍下Java内存模型以及我们前篇文章提到的重排序概念. volatile 在前一…
一 引言 听说在Java 5之前volatile关键字备受争议,所以本文也不讨论1.5版本之前的volatile.本文主要针对1.5后即JSR-133针对volatile做了强化后的了解. 二 volatile的特性 开门见山,volatile变量自身具有以下特性: 可见性(最重要的特性).对一个volatile变量的读,总是能看到(任意线程)对这个volatile变量最后的写入. 原子性.对任意(包括64位long类型和double类型)单个volatile变量的读/写具有原子性.但是类型于a…
volatile 的特性 当我们声明共享变量为 volatile 后,对这个变量的读/写将会很特别.理解 volatile 特性的一个好方法是:把对 volatile 变量的单个读/写,看成是使用同一个锁对这些单个读/写操作做了同步.下面我们通过具体的示例来说明,请看下面的示例代码: class VolatileFeaturesExample { //使用volatile声明64位的long型变量 volatile long vl = 0L; public void set(long l) {…
volatile的特性 当我们声明共享变量为volatile后,对这个变量的读/写将会很特别.理解volatile特性的一个好方法是:把对volatile变量的单个读/写,看成是使用同一个监视器锁对这些单个读/写操作做了同步.下面我们通过具体的示例来说明,请看下面的示例代码: class VolatileFeaturesExample { volatile long vl = 0L; //使用volatile声明64位的long型变量 public void set(long l) { vl =…
volatile的特性 当我们声明共享变量为volatile后,对这个变量的读/写将会非常特别. 理解volatile特性的一个好方法是:把对volatile变量的单个读/写,看成是使用同一个监视器锁对这些单个读/写操作做了同步. 以下我们通过详细的演示样例来说明,请看以下的演示样例代码: class VolatileFeaturesExample { volatile long vl = 0L; //使用volatile声明64位的long型变量 public void set(long l)…
Java内存模型JMM java内存模型定义 上一遍文章我们讲到了CPU缓存一致性以及内存屏障问题.那么Java作为一个跨平台的语言,它的实现要面对不同的底层硬件系统,设计一个中间层模型来屏蔽底层的硬件差异,给上层的开发者一个一致的使用接口.Java内存模型就是这样一个中间层的模型,它为程序员屏蔽了底层的硬件实现细节,支持大部分的主流硬件平台. java内存模型(Java Memory Mode):java内存模型是java虚拟机内存如何与计算机内存(RAM)一起工作.java虚拟机是是整个计算…
简介 Java内存模型英文叫做(Java Memory Model),简称为JMM.Java虚拟机规范试图定义一种Java内存模型来屏蔽掉各种硬件和系统的内存访问差异,实现平台无关性. CPU和缓存一致性 讲JMM之前,我们应该先了解下CPU和缓存一致性的问题.计算机在执行程序的时候,每条指令都是在CPU中执行的,而执行的时候,又要和数据打交道.而计算机上面的数据,是存放在内存当中的.随着CPU的高速发展,从内存中读取和写入数据的过程和CPU的执行速度比起来差距就会越来越大,这导致了CPU不能满…
一.Java内存模型(jmm) 线程通信 消息传递 重排序 顺序一致性 Happens-Before As-If-Serial…
如果要了解Java内存模型,就得对多线程的三大特性有初步的了解. 1.原子性:独一无二.一个操作或者多个操作 要么全部执行并且执行的过程不会被任何因素打断,要么就都不执行.比如i = i+1:其中就包括,读取i的值,计算i,写入i.这行代码在Java中是不具备原子性的,则多线程运行肯定会出问题,所以也需要我们使用同步和lock这些东西来确保这个特性了.原子性其实就是保证数据一致.线程安全. 2.可见性:当多个线程访问同一个变量时,一个线程修改了这个变量的值,其他线程能够"立即"看得到修…
前言 今天我们继续学习并发.在之前我们学习了 JMM 的知识,知道了在并发编程中,为了保证线程的安全性,需要保证线程的原子性,可见性,有序性.其中,synchronized 高频出现,因为他既保证了原子性,也保证了可见性和有序性.为什么,因为 synchronized 是锁.通过锁,可以让原本并行的任务变成串行.然而如你所见,这也导致了严重的性能受损.因此,不到万不得已,不要使用锁,特别是吞吐量要求特别高的 WEB 服务器.如果锁住,性能将呈几何级下降. 但我们仍然需要锁,在某些操作共享变量的时…
一.重入锁 锁作为并发共享数据,保证一致性的工具,在JAVA平台有多种实现(如 synchronized(重量级) 和 ReentrantLock(轻量级)等等 ) .这些已经写好提供的锁为我们开发提供了便利. 重入锁,也叫做递归锁,指的是同一线程 外层函数获得锁之后 ,内层递归函数仍然有获取该锁的代码,但不受影响. 在JAVA环境下 ReentrantLock 和synchronized 都是 可重入锁 synchronized: public class Test implements Ru…
1. I/O模型介绍 1.1 I/O模型基础 更好的理解I/O模型,需要先回顾:同步.异步.阻塞.非阻塞 同步:执行完代码后,原地等待,直至出现结果 异步:执行完代码后,不等待,继续执行其他事务(常与回调机制关联) 阻塞:cpu在遇到I/O操作,进入阻塞状态,cpu切换到其他任务 非阻塞:不会遇到I/O操作,cpu一直处于计算状态 注:同步不等于阻塞 I/O模型总计有五种,其中信号驱动I/O,在实际中并不常用,主要还是学习另外四种I/O模型 阻塞I/O模型(blocking IO) 非阻塞I/O…
1.I/O模型介绍 同步(synchronous) IO和异步(asynchronous) IO,阻塞(blocking) IO和非阻塞(non-blocking)IO分别是什么,到底有什么区别?这个问题其实不同的人给出的答案都可能不同,比如wiki,就认为asynchronous IO和non-blocking IO是一个东西.这其实是因为不同的人的知识背景不同,并且在讨论这个问题的时候上下文(context)也不相同.所以,为了更好的回答这个问题,我先限定一下本文的上下文. 本文讨论的背景是…
一,Condition 一个场景,两个线程数数,同时启动两个线程,线程A数1.2.3,然后线程B数4.5.6,最后线程A数7.8.9,程序结束,这涉及到线程之间的通信. public class ConditionTest { static class NumberWrapper { public int value = 1; } public static void main(String[] args) { //初始化可重入锁 final Lock lock = new ReentrantL…
深入理解Java内存模型JMM与volatile关键字 多核并发缓存架构 Java内存模型 Java线程内存模型跟CPU缓存模型类似,是基于CPU缓存模型来建立的,Java线程内存模型是标准化的,屏蔽掉了底层不同计算机的区别. 例子 编写代码来分析 public class VolatileVisibilityTest { private static boolean initFlag = false; public static void main(String[] args) throws…
volatile变量提供了最轻量级的同步机制,当一个变量加上volatile修饰时,会具有一下两个特性 https://blog.csdn.net/u011277123/article/details/72235927 1:保证此变量对所有线程的可见性,当volatile变量修改后,其它线程会立即知道该变量修改后的值. volatile变量只能保证可见性,不能保证线程安全,因为可能修改volatile变量之后,虽然其它线程已经知道该值变化,但是其它线程之前已经读取了该变量的值,还是按照原来的值进…
Java内存模型是保障多线程安全的根基,这里不过认识型的理解总结并未深入研究. 一.什么是内存模型,为什么须要它 Java内存模型(Java Memory Model)并发相关的安全公布,同步策略的规范.一致性等都来自于JMM. 1 平台的内存模型 在架构定义的内存模型中将告诉应用程序能够从内存系统中获得如何的保证,此外还定义了一些特殊的指令(称为内存栅栏或栅栏),当须要共享数据时,这些指令就能实现额外的存储协调保证. JVM通过在适当的位置上插入内存栅栏来屏蔽在JVM与底层平台内存模型之间的差…
原文:多线程之Java内存模型(JMM)(一) 概述 多任务和高并发是衡量一台计算机处理器的能力重要指标之一.一般衡量一个服务器性能的高低好坏,使用每秒事务处理数(Transactions Per Second,TPS)这个指标比较能说明问题,它代表着一秒内服务器平均能响应的请求数,而TPS值与程序的并发能力有着非常密切的关系.在讨论Java内存模型和线程之前,先简单介绍一下硬件的效率与一致性. 硬件的效率与一致性 由于计算机的存储设备与处理器的运算能力之间有几个数量级的差距,所以现代计算机系统…
Java内存模型(JMM):描述了java程序中各种变量(线程共享变量)的范根规则,以及在JVM中将变量存储到内存和从内存中读取出变量这样的底层细节.共享变量就是指一个线程中的变量在其他线程中也是可见的. 什么是内存模型? 在多核系统中,处理器一般有一层或者多层的缓存,这些的缓存通过加速数据访问(因为数据距离处理器更近)和降低共享内存在总线上的通讯(因为本地缓存能够满足许多内存操作)来提高CPU性能.缓存能够大大提升性能,但是它们也带来了许多挑战.例如,当两个CPU同时检查相同的内存地址时会发生…
鲁迅曾经说过“并发处理的广泛应用是使得Amdahl定律代替摩尔定律成为计算机性能发展源动力的根本原因,也是人类‘压榨‘ 计算机运行能力的最有力武器.” 一.概述 多任务处理在现代计算机操作系统中几乎已是一项必备的功能了.在许多情况下让计算机同时去做几件事情,不仅是因为计算机的运算能力强大了,还有一个重要的原因是计算机的运算速度与它的存储和通信子系统的差距太大,大量的时间都花费在磁盘 I/O .网络通信或者数据库访问上.如果不希望处理器在大部分时间里都是处于等待其他资源的状态,就必须使用一些手段去…
原文:http://www.cs.umd.edu/~pugh/java/memoryModel/jsr-133-faq.html 第一章 译者:方腾飞 在多核系统中,处理器一般有一层或者多层的缓存,这些的缓存通过加速数据访问(因为数据距离处理器更近)和降低共享内存在总线上的通讯(因为本地缓存能够满足许多内存操作)来提高CPU性能.缓存能够大大提升性能,但是它们也带来了许多挑战.例如,当两个CPU同时检查相同的内存地址时会发生什么?在什么样的条件下它们会看到相同的值? 在处理器层面上,内存模型定义…
概述 多任务处理在现代计算机操作系统中几乎已是一项必备的功能了.在许多情况下,让计算机同时去做几件事情,不仅是因为计算机的运算能力强大了,还有一个很重要的原因是计算机的运算速度与它的存储和通信子系统速度的差距太大,大量的时间都花费在磁盘I/O.网络通信或者数据库访问上.如果不希望处理器在大部分时间里都处于等待其他资源的状态,就必须使用一些手段去把处理器的运算能力“压榨”出来,否则就会造成很大的浪费,而让计算机同时处理几项任务则是最容易想到.也被证明是非常有效的“压榨”手段. 除了充分利用计算机处…
面试官:我记得上一次已经问过了为什么要有Java内存模型 面试官:我记得你的最终答案是:Java为了屏蔽硬件和操作系统访问内存的各种差异,提出了「Java内存模型」的规范,保证了Java程序在各种平台下对内存的访问都能得到一致效果 候选者:嗯,对的 面试官:要不,你今天再来讲讲Java内存模型这里边的内容呗? 候选者:嗯,在讲之前还是得强调下:Java内存模型它是一种「规范」,Java虚拟机会实现这个规范. 候选者:Java内存模型主要的内容,我个人觉得有以下几块吧 候选者:1. Java内存模…