概述
应用程序在启动的时候需要启动虚拟机进行加载class文件到内存中。然后等待程序的调用。那么有时候我们的程序回报一个错误:
ClassNotFoundException异常。什么情况下会报这个异常呢?也许你会说jvm找不到类。但是jvm它是怎么进行加载的呢?加载的机制是怎么样的?
jvm采用委托上级的加载机制加载类。那么jvm的加载器自上而下四个:
BootStraptClassLoader:虚拟机启动时加载虚拟机内部的class文件。引导加载器
ExtClassLoader:扩展类加载器加载jdk目录下ext目录里面的jar。如图:扩展类加载器
applicationClassLoader:应用加载器,加载应用classpath目录下的文件。也就是应用代码编译后的文件
customerClassLoader 用户自定义加载器。最后是用户自定义类加载器
整个加载过程采用委托上层加载器加载。自上而下,在各自的加载区域加载文件,如果到customerClassLoader仍
找不到文件,就会爆出CllassNotFourndException 异常,退出程序。
TOMCAT的加载机制:下面是tomcat的目录
Bootstramp: 加载虚拟机所需的jar.以及jdk中标准的扩展类jre/lib/ext目录下面
System: 加载tomcat启动文件catalina.bat文件中指定的类
Common:加载tomcat的lib包下面的类。
最后加载应用加载器首先加载CLASSPATH ,其次加载 WEB-INFO/lib目录下的jar文件
当应用需要到某个类时,则会按照下面的顺序进行类加载:
1、使用bootstrap引导类加载器加载
2、使用system系统类加载器加载
3、使用应用类加载器在WEB-INF/classes中加载
4、使用应用类加载器在WEB-INF/lib中加载
5、使用common类加载器在CATALINA_HOME/lib中加载
问题扩展
通过对上面tomcat类加载机制的理解,就不难明白 为什么java文件放在Eclipse中的src文件夹下会优先jar包中的class?
这是因为Eclipse中的src文件夹中的文件java以及webContent中的JSP都会在tomcat启动时,被编译成class文件放在 WEB-INF/class中。
而Eclipse外部引用的jar包,则相当于放在 WEB-INF/lib 中。
因此肯定是 java文件或者JSP文件编译出的class优先加载。
通过这样,我们就可以简单的把java文件放置在src文件夹中,通过对该java文件的修改以及调试,便于学习拥有源码java文件、却没有打包成xxx-source的jar包。
另外呢,开发者也会因为粗心而犯下面的错误。
在 CATALINA_HOME/lib 以及 WEB-INF/lib 中放置了 不同版本的jar包,此时就会导致某些情况下报加载不到类的错误。
还有如果多个应用使用同一jar包文件,当放置了多份,就可能导致 多个应用间 出现类加载不到的错误。
最后
以上就是激昂冥王星为你收集整理的jvm类加载和tomcat类加载机制的全部内容,希望文章能够帮你解决jvm类加载和tomcat类加载机制所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复