Java内存模型及其它

先来说一说一些别的东西。

1.Java内存分配:

  • 对象优先在Eden区分配

  • 大对象直接进入老年代
    大对象其实就是需要大量连续空间的Java对象,例如:很长的字符串以及数组。
    虚拟机提供了一个PretenureSizeThreshold参数,大于这个参数设置值的对象直接在老年代分配空间。这样主要是为了避免在Eden区和Survivor区发生大量的内存复制。

  • 长期存活的对象进入老年代
    对象晋升到老年代的年龄阈值,可以通过参数MaxTenuringThreshold来观察,一般默认年龄到达15岁后,进入老年代。

2.Java动态对象的年龄判定:
如果在Survivor空间中相同年龄的所有对象大小的总和大于Survivor空间的一半,则大于等于该年龄的对象就可以直接进入老年代,不需要等到15岁。

3.JDK中常用的JVM检测工具:
主要是命令行工具:

  • jps:虚拟机进程状态工具
    jps -l :可以列出当前正在执行的虚拟机进程,并返回这些进程的唯一ID

    在打开IDEA之前:
    在这里插入图片描述
    打开IDEA后:
    在这里插入图片描述

  • jmap:内存映像工具
    jmap -heap ID:显示Java堆的详细信息
    jmap -histo ID:显示对象的统计信息
    jmap -dump:生成Java堆的转储快照

  • jstack:Java堆栈跟踪工具
    用来生成虚拟机当前线程快照,从而定位线程出现长时间停顿的原因。
    jstack -l:显示关于锁的附加信息

4.Java内存模型:(JMM)

1)目的:屏蔽各种硬件和操作系统的内存访问差异,实现一致的访问效果。
2)主要目标:定义变量的访问规则(不包含局部变量和方法参数),其实就是如何将变量从内存中取出以及如何将变量写入内存等细节。
3)线程、工作内存与主内存的交互关系:

  • 每条线程都有自己的工作内存,不同线程之间无法访问对方工作内存中的变量
  • 所有的变量都必须存储在主内存中,线程中的工作内存不过是保存了该线程使用到的变量的副本
  • 线程对变量的所有操作都必须在工作内存中进行,而不能直接读写主内存中的变量,线程间变量值的传递需要通过主内存来完成。

我们来画图举例说明:
在这里插入图片描述
当一个线程需要对一个共享变量进行读写操作的时候:
第一步:将主内存中的共享变量拷贝到该线程自己的工作内存中;
第二步:在自己的工作内存中进行修改(例如:赋值)
第三步:将修改后的共享变量的值写回到主内存中(即更新该共享变量的值)
在实现以上操作时,每条操作必须都是原子的、不可再分的。

  • 为什么要保证原子性呢?
    因为这样可以保证线程是安全的。

5.那我们来想一想为什么会线程不安全呢?
假如现在有两个线程同时从主内存中拿到了一个共享变量(假设值为1),并且都对它进行操作(假如这个操作是+1),我们预期的结果是这个共享变量的值是3,因为进行了两次相加操作,但结果是2,因为实际上写回主内存的值只进行了一次相加操作。

6.只有当以下三个特性同时满足的情况才是线程安全的:

  • 原子性:一个或多个操作在CPU的执行过程不会被打断。
    例如:基本数据类型的访问(读写操作)是满足原子性的。
    但加减操作不具备原子性。
  • 可见性:当一个线程修改了共享变量的值,其他线程能够立即得知此修改。
    拿我们刚才举得例子来说:线程1拿到值后,进行加一操作值变为2;此时若满足可见性,则线程2会立即得知此修改,再进行加一操作变为3,此时写回主内存的值就是我们期望的值,解决了线程不安全的问题。
    其实多线程同步就是保证了原子性和可见性。
  • 有序性:即就是按照代码的顺序依次进行。
    一段代码可能在我们的线程内看是有序的,但是在其他线程看来就是无序的。
    JMM具有先天的有序性,即不用任何操作就能保证代码是有序的,这称为JMM的happens-before原则。若不满足该原则,JVM会进行指令重排。

7.volatile关键字:
volatile是轻量级同步关键字,用来修饰变量。

  • volatile关键字用来保证可见性(每个线程对变量的修改对其他线程都是立即可知的)
  • volatile关键字可以保证有序性:volatile变量前的语句一定优先于volatile变量之后的语句执行。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值