JVM内存管理学习笔记
问题实例分析
定义:String s1 = “uml”; String s2 = “uml”; String s3= new String(“uml”); String s4= new String(“uml”);那么,s1==s2;s3 == s4;s1.equals(s3); 判断正确与否
堆用于存放几乎所有的对象实例和数组,方法去存储运行的常量值,虚拟机栈存储局部变量表。
“equals”比较的是值,“==”比较的是地址和值
所以可得:
- s1 == s2,两个引用指向同一个值和地址,返回true。
- s3 == s4,两个都是new出来的对象,值相同但是地址不同,返回false。
- s1.equals(s3)比较的是值,返回true。
JVM模型
程序计数器(Program Counter Register)
- 是当前线程所执行的字节码的行号指示器
- 如果线程正在执行的是一个Java方法,那么计数器记录的是正在执行的虚拟机字节码指令的地址;
- 如果线程正在执行的是一个Native方法,那么计数器的值则为空。
Java虚拟机栈(Java Virtual Machine Stacks)
-
是Java方法执行的内存模型
-
每个方法在执行的同时都会创建一个栈帧,用于存储局部变量表、操作数栈、动态链接、方法出口等信息。
-
每一个方法从调用直至执行完成的过程,就对应着一个栈帧在虚拟机栈中入栈到出栈的过程。
-
本地方法栈(Native Method Stack)
- 是虚拟机使用到的Native方法服务。
- 在虚拟机规范中,对这个区域无强制规定,由具体的虚拟机自由实现。与虚拟机栈一样,本地方法栈区域也会抛出StackOverflowError和OutOfMemoryError异常。
Java堆(Java Heap)
- 用于存放几乎所有的对象实例和数组。
- 被所有线程共享的一块内存区域,在虚拟机启动时创建。
- 是垃圾收集器管理的主要区域,也被称做“GC堆”。
- 是Java虚拟机所管理的内存中最大的一块。
- 可处于物理上不连续的内存空间中,只要逻辑上是连续的即可。
- 在Java虚拟机规范中,如果在堆中没有内存完成实例分配,且堆也无法再扩展时,将会抛出OutOfMemoryError异常。
方法区(Method Area)
-
用于存储已被虚拟机加载的类信息、常量、静态变量、即时编译器编译后的代码等数据。
-
与Java堆一样,是各个线程共享的内存区域。
-
人们更愿意把这个区域称为**“永久代”(Permanent Generation),在发布的JDK1.7的HotSpot中,已经把原本放在永久代的字符串常量池移出。它还有个别名叫做Non-Heap(非堆)**。
-
和Java堆一样不需要连续的内存和可以选择固定大小或可扩展外,还可选择不实现GC。
-
在Java虚拟机规范中,当方法区无法满足内存分配需求时,将抛出OutOfMemoryError异常。
择不实现GC。
- 在Java虚拟机规范中,当方法区无法满足内存分配需求时,将抛出OutOfMemoryError异常。