`

Java并发编程学习前期知识下篇

 
阅读更多

Java并发编程学习前期知识下篇

通过上一篇《Java并发编程学习前期知识上篇》我们知道了在Java并发中的可见性是什么?volatile的定义以及JMM的定义。我们先来看看几个大厂真实的面试题:

编辑
编辑
编辑

从上面几个真实的面试问题来看,我们可以看到大厂的面试都会问到并发相关的问题。所以

Java并发,这个无论是面试还是在工作中,并发都是会遇到的。Java并发包JUC(java.util.concurrent)有了解过哪些?并发包实现最重要的是什么?其原理是什么知道吗?何为JMM的可见性?volatiile关键字是怎么实现变量可见性的?如果想要学好并发,弄懂理解透彻的话,凯哥觉得以下计算机的知识还是要了解了解。本次《Java并发编程-前期准备知识》凯哥准备用两篇来介绍,主要包括以下内容:简单介绍内存之间可见性是什么?volatile关键字在Java语言规范中是怎么定义的?知道JVM但是你知道JMM是什么吗?计算机中CPU是怎么处理数据的?通过CPU处理数据来深刻理解线程之间可见性。还有就是volatile是怎么保证可见性的呢?其实现的两条原理是什么?

CPU相关知识

先来看看凯哥电脑配置:

编辑
编辑
编辑

从上图,可以看到凯哥电脑

CPU处理是4核8线程,

缓存有三级。

其中一级数据缓存和指令缓存都是32K,

二级缓存256K,

三级缓存是6M.

电脑的内存是24G

为什么要说这些呢 ?

因为JVM运行程序的实体其实就是线程,而每个线程在创建的时候JVM都会给其创建一个工作内存(有些地方称之为:栈空间)。工作内存是每个线程自己的私有数据区域。Java内存模型中规定所有的变量都是存储在主内存中(也就是凯哥24G内内存中),主内存是共享内存区域,所有的线程都可以访问的(也就是说主内存中的数据,任意线程都可以访问)。但是线程对变量的操作,如读取,修改赋值操作是在从中内存中进行的。因此,一个线程要想操作一个变量,首先是要讲变量从主内存copy到自己的工作内存空间,然后再对自己工作空间中对变量操作,操作完成之后再将变量写回到主内存中去。线程是不能够直接操作主内存中的变量的。各个线程中的工作内存存储的其实就是主内存的一个变量副本拷贝。因此不同线程之间是无法访问到对方的工作内存的。线程间的通讯(值转递)必须通过主内存来完成的。

上面这么大一段话,可以简单对应凯哥电脑配置:

线程:其实就是凯哥CPU的4核8线程中的线程

主内存:就是凯哥本子上的24G物理内存条

线程工作内存空间:就是缓存(一二三级缓存区域)

线程工作原理,如下图:

编辑

说明:

主内存中变量int i= 0;

cpu1中的线程1获取到i变量的时候,会将i从主内存中copy一份到自己的工作区域,也就是cpu1 cache中,然后更新i的值为10;

cpu2中的线程2同样获取到i变量,从主内存中copy一份之后,在自己的工作区cpu2 cache中将i修改成了15;这种情况下就是多核多线程问题。

线程之间可见性深度理解

在这种情况下主内存中的i就是两个线程之间的共享变量了。那么怎么能确保cpu1的线程1修改i的值之后,通知cpu2中的线程2的工作区缓存无效呢?这个操作就是线程之间的可见性。

再举个现实生活中常用的例子:

比如,凯哥现在在和大家分享。今天我发布之后,你们大家在自己手机或者是PC网友上都能看到凯哥分享的知识点。这个时候有个网友A在看到凯哥分享的东西,感觉有点不好或者是举个其他的例子或者更容易理解。于是他把凯哥这个文章进行了修改。然后给凯哥留Y。告诉凯哥,凯哥看后,觉得很不错。等明天,凯哥发文章通知大家,如果用xxx的案例就跟容易让大家理解了。于是,你们大家知道,哦原来昨天的案例不是最新的了。放弃昨天的,看看今天最新的案例。

如果上面案例看着是多线程那么可以这么分析:

主内存:凯哥

共享变量:凯哥分享的知识点

多个线程:各位看凯哥分享的网友

其中网友A修改了知识点的内容(网友A修改的是自己手机上的(工作区的)知识点)后通知了凯哥,然后凯哥又通知了各位。各位知道原来自己手里的不是最新的了,然后放弃重新获取最新的。

这样来理解的话,就更容易理解线程的可见性

Volatitle是如何保证可见性的呢?

可以通过JIT编译器生成的汇编指令来查看对volatile进行写操作时候,CPU都做了哪些事情?

如下代码:

Volatile Singleton instance = new Singleton();

Instance是被volatitle修饰的。

在使用JIT编译器生成的汇编指令后,有一个重要的代码:

0x01a2de1d:xxxx:lock addl $0X0,(%esp);

我们可以看到,当一个共享变量被volatile修饰之后,在进行写操作的时候,会多出一些汇编代码Lock.在IA-32架构软件开发手册中,Lock前缀的指令当在多核处理器的时候会引发出两件事情:

1:将当前的处理器缓存行的数据写回的主内存中(也就是系统的物理缓存中);

2:同时这个写回内存的操作也会使其他CUP里缓存了内存地址的数据被置为无效。

Cpu处理数据方法:

为了提高处理数据,CPU不会直接从内存中获取数据操作的。

这里我们需要电脑处理数据的速度排序:磁盘(硬盘)<内存<高速缓存<CPU。我们可以看出CPU的操作速度比内存快很多。所以,如果CPU直接操作内存,不仅会影响处理速度还有可能让内存使用寿命变短。这个时候,高速缓存就解决这个问题的。

所以,CPU在处理数据的时候会像将内存中的数据到期到高级缓存中(就是一二三级缓存),然后再缓存中进行操作的。

在多核处理器的时候,为了保证各个处理器之间缓存变量是一致的,就需要实现缓存一致性协议。其操作就是:各个CPU通过嗅探在总线上传播的数据来实时检查自己缓存的值是不是已经过期了。如果发下自己缓存中的数据已经被修改了,则就会将当前的处理器中缓存数据状态设置为无效,当这个处理器需要对这个数据进行操作的似乎和,会重新从主内存中,把最新的数据读取到自己缓存中。

Volatile两条实现原理

1:汇编代码的lock前缀指令会引起处理器缓存写回到主内存中。

当有lock指令的缓存,在其声言期间,能搞保证处理器可以独占任何共享的内存。同时缓存一致性会阻止同时修改由两个以上处理器缓存的内存区域数据

2:当一个处理器的缓存写回到主内存中之后,会导致其他处理器的缓存无效

这个是处理器见的控制协议来维护内部缓存的

总结:

通过这两篇《Java并发编程前期准备知识》的了解,我们知道JMM,线程之间共享数据等知识,这样再接下来学习Java并发编程就会简单一些了。接下来欢迎进入Java并发编程学习中!

 

编辑

 

0
2
分享到:
评论

相关推荐

    Java并发编程(高级篇)

    Java并发编程实践中的话:编写正确的程序并不容易,而编写...本场Chat作为Java并发编程之美系列的高级篇之二,主要讲解内容如下:(建议先阅读:Java编程之美:并发编程高级篇之一)rt.jar中Unsafe类主要函数讲解,Un

    Java多线程编程实战指南(核心篇)

    Java多线程编程实战指南(核心篇) 高清pdf带目录 随着现代处理器的生产工艺从提升处理器主频频率转向多核化,即在一块芯片上集成多个处理器内核(Core),多核处理器(Multicore Processor)离我们越来越近了――如今...

    Java并发编程示例(一):线程的创建和执行

    主要介绍了Java并发编程示例(一):线程的创建和执行,本文是系列文章的第一篇,需要的朋友可以参考下

    Java 多线程编程面试集锦20道问题解答Java多线程编程高难度面试题及解析

    本篇文章提供了20道高难度的Java多线程编程面试题及详细解析,旨在帮助开发者展示出卓越的并发编程能力。在当今高并发的应用场景下,对多线程编程的理解和应用是评估面试者的重要指标。通过这些高难度问题,您将全面...

    Java并发编程this逃逸问题总结

    本篇文章给大家详细分析了Java并发编程this逃逸的问题分享,对此有需要的朋友参考下。

    java后端学习推荐书籍清单

    《Java并发编程之美》 《Java核心技术 卷1 基础知识(原书第9版)》 《Spring源码深度解析(第2版)》 《阿里巴巴Java开发手册(华山版)》 《计算机网络--自顶向下方法+原书第6版》 《鸟哥的Linux私房菜基础篇第三...

    Java并发编程:如何创建线程?

    在前面一篇文章中已经讲述了在进程和线程的由来,来讲一下在Java中如何创建线程,让线程去执行一个子任务。下面先讲述一下Java中的应用程序和进程相关的概念知识,然后再阐述如何创建线程以及如何创建进程。下面是...

    Java并发编程示例(二):获取和设置线程信息

    主要介绍了Java并发编程示例(二):获取和设置线程信息,本文是系列文章的第二篇,本文着重讲解Thread类的几个重要属性,需要的朋友可以参考下

    深入理解高并发编程-核心技术原理

    (1) 导致并发编程频繁出问题的“幕后黑手” (2)工作了3年的程序员小菜面试高并发岗位被吊打虐哭 (3)如何解决可见性和有序性问题?这次彻底懂了! 3、实战案例篇 (1) 如何实现亿级流量下的分布式限流?这些理论你必须...

    编程思想下篇

    本资源为下篇 第1章 对象导论 1.1 抽象过程 1.2 每个对象都有一个接口 1.3 每个对象都提供服务 1.4 被隐藏的具体实现 1.5 复用具体实现 1.6 继承 1.6.1 “是一个”(is-a)与“像是一个”(is-like-a)关系 1.7 伴随...

    Java并发编程:用AQS写一把可重入锁

    之所以把这一章节叫做AQS简介而不是叫AQS详解,是因为已经有大神写过详解的文章Java并发之AQS详解,这篇文章对AQS的源码解析很透彻,博主读了之后受益匪浅,鉴于对原作者的尊重,所以如上附上原文的链接。...

    JavaHub:Java程序员学习之路,持续更新原创内容,欢迎Star

    我会根据下图中的技能点持续更新原创内容,技能列举的可能不是很完善,朋友们可以去【公众号】或【微信】给我提意见!都到这了,点个【Star】防走丢哦!原创内容公众号【JavaQ】首发,关注不迷路。...高并发编程-Reent

    JavaConcurrencyPattern:Java并发模式

    这些文章已扩充为一本书:《Java多线程编程实战指南(设计模式篇)》,由电子工业出版社出版,当当、亚马逊、京东、互动出版网、淘宝等各大书店有售。 【样章】 Active Object模式: Immutable Object模式: Two-...

    经典JAVA.EE企业应用实战.基于WEBLOGIC_JBOSS的JSF_EJB3_JPA整合开发.pdf

     本书是《轻量级java ee企业应用实战》的姊妹篇,《轻量级java ee企业应用实战》主要介绍以spring+hibernate为基础的java ee应用;本书则主要介绍以ejb 3+jpa为基础的java ee应用。ejb 3、jpa规范都属于sun公司所...

    java8集合源码分析-Road2Architect:最完整最实用的软件工程师学习指南!

    整理这些文章的初衷是做好个人知识管理,构建完整健康的知识体系,在持续输入的前提下保证有效输出。 契机是阅读了这篇文章 目录 Java基础 基础知识 容器 设计模式 JavaWeb Spring SpringMVC SpringBoot todo Spring...

    Java面试突击宝典-如何面试-如何准备

    这篇⽂章内容有点多,如果这篇⽂章只能让你记住 4 句话,那请记住下⾯这 4 句: 1. ⼀定要提前准备⾯试!技术⾯试不同于编程,编程厉害不代表技术⾯试就⼀定能过。 2. ⼀定不要对⾯试抱有侥幸⼼理。打铁还需⾃身硬...

    c#学习笔记.txt

    本文假定你具备一切学习此语言所需的知识,没有也不要紧,我会在文中尽量列出相关的link,鉴于互联网瞬息万变的特点,若某一链接不可用,请自行至Google查询。 如前所述,我是一个狮子座男人,一度我认为学习Java会...

    Java的六大问题你都懂了吗

    这些问题对于认真学习java的人都要必知的,当然如果你只是初学者就没必要那么严格了,那如果你认为自己已经超越初学者了,却不很懂这些问题,请将你自己重归初学者行列。  一、到底要怎么样初始化!  本问题讨论...

Global site tag (gtag.js) - Google Analytics