zoukankan      html  css  js  c++  java
  • Java 内存模型与内存结构

     Java内存模型


    一、简介

    Java内存模型(JMM)主要是为了规定线程和内存之间的一些关系;根据JMM的设计,系统存在一个主内存(Main Memory)和工作内存(Work Memory),Java中所有变量都储存在主内存中,对于所有线程都是共享的;每条线程都有自己的工作内存,工作内存中存储了该线程已读、写共享变量的副本,工作内存是JMM的一个抽象概念,主要包括:缓存,写缓冲区,寄存器以及其他的硬件和编译器优化;线程对所有变量的操作都是在工作内存中进行的,线程之间无法相互直接访问,变量传递均需要通过主内存完成。JMM示意图如下:

    二、JMM带来了哪些问题?

    1、可见性问题

    CPU中运行的线程从主内存中拷贝共享对象obj到它的CPU缓存,把对象obj的count变量改为2,但这个变更对运行在右边CPU中的线程不可见,因为这个更改还没有flush到主内存中,要解决共享对象可见性这个问题,可以使用 volatile 或加锁(如:synchronized),来保证可见性。

    2、竞争问题

    线程A和线程B共享一个对象obj,假设线程A从主存读取Obj.count变量到自己的CPU缓存,同时,线程B也读取了Obj.count变量到自己的CPU缓存,并且这两个线程都对Obj.count做了加1操作;此时,Obj.count加1操作被执行了两次,不过都在不同的CPU缓存中,如果这两个加1操作是串行执行的,那么Obj.count变量便会在原始值上加2,最终主存中的Obj.count的值会是3;然而如果是并行操作,不管是线程A还是线程B先flush计算结果到主存,最终主内存中的Obj.count只会增加1次变成2;可以使用加锁( 如:synchronized) 解决此问题,来保证一致性。

     3、重排序问题

    在执行程序时,为了提高性能,编译器和处理器常常会对指令做重排序。

    可以使用volatile或加锁(如:synchronized)来保证有序性。

    Java内存结构


    先看一下结构图:

    从图中可以看出Java内存结构包括五大区域:堆、方法区、虚拟机栈、本地方法栈、程序计数器,其中堆、方法区线程共享,虚拟机栈、本地方法栈、程序计数器线程私有。

    1、堆

    堆是Java虚拟机管理的最大一块内存区域,存放所有对象实例和数组,因为堆存放的对象是线程共享的,所以多线程的时候需要同步机制;堆又划分为:年轻代、老年代、永久代(JDK1.7)/元空间(JDK1.8),元空间与永久代的区别在于:永久代使用的是虚拟机内存,元空间则采用本地内存。

     

    2、虚拟机栈

    虚拟机栈描述的是线程进栈出栈的过程,线程结束内存自动释放,它用来存储当前线程运行方法所需要的数据、指令、返回地址(即局部变量和正在调用的方法),方法被调用时会在栈中开辟一块叫栈帧的空间,方法运行在栈帧空间中。

    3、本地方法栈

    本地方法栈与虚拟机栈的作用十分相似,区别是虚拟机栈执行的是Java方法服务,而本地方法栈则为虚拟机使用native方法服务,可能底层调用的c或者c++方法。

    4、方法区

    方法区同堆一样,是所有线程共享的内存区域,又被称为非堆,用于存储已被虚拟机加载的类信息、常量、静态变量等。

    5、程序计数器

    程序计数器是一块很小的内存空间,它是线程私有的,可以认作是当前线程的行号指示器。

    参考:

    [1] https://www.jianshu.com/p/8a58d8335270

    [2] https://www.jianshu.com/p/de097e7a813a

    [3] http://tutorials.jenkov.com/java-concurrency/java-memory-model.html

  • 相关阅读:
    html+php超大视频切片上传
    html+php超大视频分片上传
    html+php超大视频上传前端
    html+php超大视频上传讨论
    html+php超大视频上传分享
    MATLAB的设置视点函数view
    matlab 绘制三维图并标注每个点的坐标
    Spring Boot 五种热部署方式,极速开发就是生产力!
    如何提高服务器的并发处理能力?硬核!
    WEB攻击手段及防御第3篇-CSRF
  • 原文地址:https://www.cnblogs.com/ityard/p/11180145.html
Copyright © 2011-2022 走看看