什么是 JVM ?
定义
- Java Virtual Machine - java 程序的运行环境(java 二进制字节码的运行环境)
好处
-
一次编写,到处运行
-
自动内存管理,垃圾回收功能
-
数组下标越界检查
-
多态
-
jvm jre jdk
常见的 JVM
整体结构
内存结构
程序计数器
定义
- Program Counter Register 程序计数器(寄存器)
- 作用
- 是记住下一条 jvm 指令的执行地址,也就是线程当前要执行的指令地址
- 特点
- 线程私有
- 不会存在内存溢出(唯一)
虚拟机栈
定义
- Java Virtual Machine Stacks (Java 虚拟机栈)
- 每个线程运行时所需要的内存,称为虚拟机栈
- 每个栈由多个栈帧(Frame)组成,对应着每次方法调用时所占用的内存
- 每个线程只能有一个活动栈帧,对应着当前正在执行的那个方法
- 栈的大小
- Linux/x64(64-bit):1024 KB
- maxOS(64-bit):1024 KB
- Oracle Solaris/x64(64-bit):1024 KB
- Windows:The default value depends on virtual memory
问题
-
垃圾回收是否涉及栈内存?
不涉及。每一次方法调用之后栈帧会被弹出,释放内存,不需要垃圾回收。 -
栈内存分配越大越好吗?
不。计算机总的物理内存有限,栈内存越大,栈的数量就越少,能够开启的线程就越少 -
方法内的局部变量是否线程安全?
- 如果方法内局部变量没有逃离方法的作用访问,它是线程安全的
- 如果是局部变量引用了对象,并逃离方法的作用范围,需要考虑线程安全
栈内存溢出
- 栈帧过多导致栈内存溢出
- 栈帧过大导致栈内存溢出
public static void main(String[] args) throws Exception{
try {
method();
} catch (Exception e) {
e.printStackTrace();
} finally {
System.out.println(count);
}
}
public static void method() {
count++;
method();
}
21187
Exception in thread "main" java.lang.StackOverflowError
本地方法栈
定义
-
管理本地方法,即非 Java 语言编写的方法(C语言)的调用
-
Navtive 方法是 Java 通过 JNI 直接调用本地 C/C++ 库
-
线程私有
-
HotSpot 虚拟机直接把本地方法栈和虚拟机栈合二为一
// Object 类中有大量的本地方法
public final native Class<?> getClass();
public native int hashCode();
protected native Object clone() throws CloneNotSupportedException;
public final native void notify();
public final native void notifyAll();
public final native void wait(long timeout) throws InterruptedException;
堆
定义
-
通过 new 关键字,创建对象都会使用堆内存
-
线程共享的,堆中对象都需要考虑线程安全的问题
-
垃圾回收机制
堆内存溢出
-
创建的对象被虚拟机认为有用,不被回收,最后可能造成 OOM
-
注意不一定非得 new 对象的时候才会出现。
public static void main(String[] args) throws Exception {
String s = "a";
ArrayList<String> array = new ArrayList<>();
int count = 0;
try {
while (true) {
s += "a";
array.add(s);
count++;
}
} catch (Exception e) {
e.printStackTrace();
} finally {
System.out.println(count);
}
}
60311
Exception in thread "main" java.lang.OutOfMemoryError: Java heap space
堆内存诊断
- jps 工具
查看当前系统中有哪些 java 进程 - jmap 工具
查看堆内存占用情况 jmap - heap 进程id - jconsole 工具
图形界面的,多功能的监测工具,可以连续监测 - jvisualvm 工具
更强大的可视化工具