Jvm类加载器和双亲委派机制
1、首先一个car.class(我们加载文件编译后的文件)进入jvm,首先是进入一个class Lodear(去加载,初始化)变成一个Car class(类加载器(class Lodear)去加载初始化什么东西,就是去初始化加载我们的类啊)。而这个Car Class是去后面实例化的(这个类去实例化的嘛)
我们这里理解一下,我们自己用的一个car.class(这就是个反射Car这个类的反射对象(编译后的.class文件?))这个东西吧。他会返回一个Class对象。这个Class对象是一个类的模板反射对象(类的模板都是一样的,实例化对象都是根据这个模板去实例化的(实例化对象不一样,但是实例化的模板是一样的))。
!!!这里是我们的类的实例化对象,向上一层找我们的实例化模板对象。(对象不同,模板相同)
3、类加载器等级
1、虚拟机自带的加载器
2、启动类(根)加载器(在jdk的rt.jar里面(根)),向上委托到这
3、扩展类加载器(ExtClassLoader)
4、应用程序加载器(AppClassLoader)
我们这里根据上面的这个类的实例化对象上去找他的模板,在根据这个模板往上面找他的级别更高的加载器
这里我们分析为什么为null,我们核心的包都在jdk下面的rt.jar的java里面。其中什么long里面的最简单的String类。这些就是我们java自带的东西。所以我们才可以去使用String。
或者我们去jdk的jre的lib文件里面找
根包(是一个压缩文件,有很多东西的)
扩展包(也就是我们的jar包若是没有放在rt.jar。他也会往上找就是在这个扩展里面找)
!!!这里的报错是无法去找到String的main方法(那么它肯定走的不是这个我们写的这个main方法(这里执行的是根加载器的String类的main方法))
流程:我们这里创建了一个String类,那么我们类加载器收到这个类加载请求了。他就往上委托我们的类加载器(最开始为AppClassLoader嘛),最后到我们根加载器了(必须先委托到最上面类加载器,再从上面开始向下加载类),也就是rt.jar。(注意我们最开始的是我们的AppClassLoader,只有从上往下加载不到类才会去用我们的AppClassLoader加载我们自己写的类)
然后从这个根加载器里面就有String类啊。所以他就加载这个根加载器的类咯。
我们这样还是不行的(去这个mian里面找其中加载器。(他都根本不会到这个AppClassLoader怎么去加载我们自己类的执行mian方法))
流程是只有当我们的类被委托到最上面再往下查找加载都没有才会是我们自己的AppClassLoader加载我们自己写的类,然后执行main方法
这里是我们最上面的类的实例化对象.getClass(找到类模板).getClassLoader(找到具体的类加载器)