字节二面:JVM各区域间是如何协同工作的?
#每天一道面试题# 56
JVM可以分为运行时数据区以及类加载器、执行引擎、本地方法库
运行时数据区包含以下部分:
1.方法区:非堆
2.虚拟机栈:本地方法
3.本地方法栈:native方法
4.堆:新生代(from、to、eden)、老年代
5.程序计数器:标记当前线程所执行的位置,方便上下文切换完成以后继续执行
非运行时数据区:
6.类加载器:启动类加载器、扩展类加载器、系统类加载器、自定义类加载器;
7.执行引擎:将字节码指令解释/编译为对应平台上的本地机器指令;
8.本地方法库:Java调用跨语言(C、C++)的接口。
问题一:堆、栈、方法区之间数据存储怎么协调的?
答:栈指向方法区;栈指向堆、堆指向方法区、方法区指向堆;
栈:栈帧(局部变量表、操作数栈、返回地址、动态链接)
栈 -> 方法区
 动态链接指向 Klass 对象在方法区的地址
栈 -> 堆
 局部变量表存放的引用变量,指向真实对象存放在堆中的地址
方法区 -> 堆(JDK8以后方法区不在指向堆)
 JDK7 以前静态属性在方法区中;
 JDK8 及以后,存在堆中元数据类Class中;
堆 -> 方法区
 klass pointer 作用去找到对象依赖的类;
问题二:双亲委派机制了解吗?
答:双亲委派:沙箱安全机制,防止核心API库被随意篡改。
还有一些场景破坏了双亲委派机制,因为受类加载器受到加载范围的限制,存在某些情况下父类加载器无法加载到需要的文件。在JDBC、Tomcat、OSGI 场景就需要委托子类加载器去加载class文件破坏了双亲委派机制。
问题三:内存分配策略了解吗?
答:空闲列表:idle(空闲),used(已用),available(可用);
指针碰撞:自旋 + CAS;
问题四:为什么要引入元空间?
1.永久代缺点
 存在内存瓶颈
 GC:字符串常量池,动态字节码
 存储类信息
2.元空间能解决永久代问题,它本身还存在问题吗?
 元空间存储应用程序的类加载器信息,当前实现回收以后会产生内存碎片
问题五:方法区,元空间,永久代之间关系?
方法区是JVM的规范;元空间与永久代是规范落地实现,7叫永久代在JVM内部,8及以后叫元空间使用直接内存; 容易混淆的概念:
堆空间不是全部被线程共享的,TLAB:线程私有的堆空间
对象不一定存放在堆中,方法内局部变量,存在栈中
元空间不等于方法区,方法区抛开元空间以外还包括CodeCache存储JIT的代码等。
 
 
                     
            
        













 
                    

 
                 
                    