Java基础-JVM

JVM构成部分

类加载系统

类加载子系统的作用是将磁盘中的.class文件加载到内存当中。工作过程如下:

  • 加载:通过类全路径名获取二进制字节流 ;将这个二进制字节流代表的数存储构转化为方法区运行时数据结构 ;在内存生成一个代表该类的Class对象,作为方法区该类的访问入口。
  • 链接
    • 验证:验证加载的.class文件是否正确
    • 准备:为static对象分配内存并赋零值
    • 解析:符号引用(一组能描述目标对象的字面量,如全路径名)解析为直接引用(指向目标对象的指针,相对偏移量或能间接定位目标的句柄)
  • 初始化:给对象赋真实的值

类加载器

用于实现类的加载动作,对于任意一个类,都必须由加载它的类加载器和这个类本身一起共同确立其在Java虚拟机中的唯一性,每 一个类加载器,都拥有一个独立的类名称空间。比较两个类是否"相等",只有在这两个类是由同一个类加载器加载的前提下才有意义,否则,即使这两个类来源于同一个 Class文件,被同一个Java虚拟机加载,只要加载它们的类加载器不同,那这两个类就必定不相等。

  • 引导类类加载器()
    • BootstrapClassLoader:加载jre中ib目录下的类
  • 自定义类加载器(继承ClassLoader抽象类)
    • ExtClassLoader:加载jre中ib/ext目录下的类
    • AppClassLoader:加载当前项目classpath下的类

双亲委派

工作过程是:类加载器收到了类加载的请求,它首先不会自己去尝试加载这个类,而是把这个请求委派给父类加载器去完成,每一个层次的类加载器都是如此,因此所有的 加载请求最终都应该传送到最顶层的启动类加载器中,只有当父加载器反馈自己无法完成这个加载请 求(它的搜索范围中没有找到所需的类)时,子加载器才会尝试自己去完成加载。双亲委派实现:

java 复制代码
    protected Class<?> loadClass(String name, boolean resolve) throws ClassNotFoundException {
        synchronized (getClassLoadingLock(name)) {
            // First, check if the class has already been loaded
            Class<?> c = findLoadedClass(name);
            if (c == null) {
                long t0 = System.nanoTime();
                try {
                    if (parent != null) {
                        c = parent.loadClass(name, false);
                    } else {
                        c = findBootstrapClassOrNull(name);
                    }
                } catch (ClassNotFoundException e) {
                    // ClassNotFoundException thrown if class not found
                    // from the non-null parent class loader
                }
                
                if (c == null) {
                    // If still not found, then invoke findClass in order
                    // to find the class.
                    long t1 = System.nanoTime();
                    c = findClass(name);

                    // this is the defining class loader; record the stats
                    sun.misc.PerfCounter.getParentDelegationTime().addTime(t1 - t0);
                    sun.misc.PerfCounter.getFindClassTime().addElapsedTimeFrom(t1);
                    sun.misc.PerfCounter.getFindClasses().increment();
                }
            }
            if (resolve) {
                resolveClass(c);
            }
            return c;
        }
    }
相关推荐
Xiaok10181 分钟前
解决 Hugging Face SentenceTransformer 下载失败的完整指南:ProxyError、SSLError与手动下载方案
开发语言·神经网络·php
ゞ 正在缓冲99%…3 分钟前
leetcode76.最小覆盖子串
java·算法·leetcode·字符串·双指针·滑动窗口
绿草在线3 分钟前
Mock.js虚拟接口
开发语言·javascript·ecmascript
go_bai14 分钟前
Linux环境基础开发工具——(2)vim
linux·开发语言·经验分享·笔记·vim·学习方法
小郝 小郝15 分钟前
【C语言】strstr查找字符串函数
c语言·开发语言
Seven9717 分钟前
【Guava】并发编程ListenableFuture&Service
java
WannaRunning18 分钟前
浅谈Tomcat数据源连接池
java·oracle·tomcat
yinhezhanshen21 分钟前
理解rust里面的copy和clone
开发语言·后端·rust
forestsea25 分钟前
使用 Spring Boot 和 GraalVM 的原生镜像
java·spring boot·spring native·原生映像
逸狼28 分钟前
【JavaEE进阶】Spring AOP入门
java·java-ee