这个文章我们要学会的内容:
---------------------------------------------------------------------------------------------------
1class装载验证的流程 :
class作为一个文件被装载到虚拟机上去经过这个几个过程:
三步:
在链接这个过程中又分为:验证,准备,解析。
我们先来分析加载这个过程:
(1)取得类的二进制流
各种途径加载,jar或者网络中。
(2)转为方法区的数据结构
(3)在java中生成对应的java.lang.class.
加载完了之后就是链接的过程了,链接可以被分为三个步骤(验证,准备,解析):
1:链接的第一步就是做验证:
验证的目的是为了保证Class流的格式是正确的。
具体的验证过程如下:
(1)------文件格式的验证
(a) --是否是0xCAFEBABE开头的
(b)--版本号是否合理:比如你的jdk6区运行jdk7生成的文件就不行。
(2)-------元数据的验证
(a)---是否有父类
(b)----是否继承了finale类
(c)------非抽象类实现了所有的抽象方法
(3)-------- 字节码的验证
(a)---运行检查
(b)---栈数据类型和操作码数据的参数吻合
(c)-----跳转指令指定到合理的位置
(4)------符号引用验证
(a)常量池中描述类是否存在
(b)访问的方法或者字段是否存在且有足够的权限
2:准备
3:解析
符号引用:简单来讲就是一个字符串。只是一种表示方式,我们要用直接引用
直接引用:就是指向地址了,就是知道在内存里面到底放在哪里。符号引用要被替换成直接引用。这样这个class在执行过程中才能找到他要用的内容。
链接的下一步就是初始化了。
问题:Java.lang.NosuchFieldError错误什么阶段抛出?
-------------------------------------------------------------------------------------------------------------
类装载器ClassLoader:
1什么是类装载器ClassLoader:
(1) ClassLoader是一个抽象类。
(2)ClassLoader的实例将读入Java字节码将类装载到JVM中
(3)ClassLoader可以定制,满足不同字节码流的获取方式
(4)ClassLoader负责类装载过程中的加载阶段
2:classLoader的重要方法:
3:ClassLoad的类加载顺序
上图中就是类加载的顺序:
自底向上去做加载。第一步:我们写的类都是在App ClassLoader里面的,如果在App ClassLoader那里找不到就去父类ExtensionClassLoader里面去找,如果ExtensionClassLoader也找不到的话,就去父类Bootstrap ClassLoader(启动Class类)里面去找,如果Bootstrap ClassLoader有那就返回就好了,如果没有,说明这一整个系统中都没有,那就只好去加载了。加载的顺序是:先是Bootstrap ClassLoader去加载,如果加载成功了就返回这个类好了,就不需要ExtensionClassLoader去加载了,如果
Bootstrap ClassLoader加载类失败了,那就只好ExtensionClassLoader去加载了。。
上面的那种类加载模式就是双亲模式。双亲模式是默认的模式,但是不是必须要这么做的:
我们 举一个例子来说明破坏双亲模式的加载模式,从底层ClassLoad来加载:
findClass(name):是指先在自己那里去做加载,自己去做查找类,加载类的工作。如果找不到再去父类里面去做加载。
举例: