方法区
方法区
堆、栈、方法去关系


方法区
虽然规范当中规定方法区在逻辑上可以看作堆的一部分,但是hostpot虚拟机认为方法区为为单独的一部分。
方法区大小设置
可以固定大小或者自动调节大小

如何解决OOM和heap space异常?
首先判断是内存溢出还是内存泄漏(什么是内存泄漏:一个不再被程序使用的对象或变量一直被占据在内存中;)
内存泄漏:
原文链接: 链接.
如果是内存泄漏就找到内存泄漏位置,如果纯粹是内存溢出,就通过修改堆内存大小(Xms和Xmx)或者修改对象生命周期等方法。
方法区内部结构

具体细分

类型信息

域信息

方法

静态变量访问
这里通过引用调用对象,即使是赋值为null,也可以访问,因为后台是通过转换为直接通过类进行调用方法和引用


运行时常量池

字节码内部常量池
Constant pool:
#1 = Methodref #6.#20 // java/lang/Object."<init>":()V
#2 = Fieldref #5.#21 // com/company/test/jvm/ClinitStudy.i:I
#3 = Fieldref #22.#23 // java/lang/System.out:Ljava/io/PrintStream;
#4 = Methodref #24.#25 // java/io/PrintStream.println:(I)V
#5 = Class #26 // com/company/test/jvm/ClinitStudy
#6 = Class #27 // java/lang/Object
#7 = Utf8 i
#8 = Utf8 I
#9 = Utf8 <init>
#10 = Utf8 ()V
。。。。。。


简而言之,就是一些引用信息的保存,在运行时可以通过保存的信息调用变量或者类等。就是一张表,方便查找使用的数值、字符串、类型信息引用、方法等。

运行时常量池


在JDK8之前,静态变量引用一直放在方法去当中,8开始,放在堆空间当中,实例变量一直放在堆空间当中,而真则真正的实例对象是一直放在堆内存当中。
为什么要把永久带改为元空间?


StringTable 为什么要放到堆区?

方法区的垃圾回收

常量的回收

类回收 如上
结构总结

面试题


本文深入探讨了Java虚拟机(JVM)的方法区,包括其与堆栈的关系、大小设置及其在解决OOM和Heapspace异常中的策略。方法区存储类型信息、域信息、方法和静态变量,其中运行时常量池用于保存字节码的常量信息。JDK8之后,永久代被替换为元空间,以减少对Java堆的压力。此外,StringTable被移到堆区以优化内存使用。文章还讨论了方法区的垃圾回收,包括常量和类的回收。







被折叠的 条评论
为什么被折叠?



