首页 / JAVA / Java中ClassLoader
Java中ClassLoader
内容导读
互联网集市收集整理的这篇技术教程文章主要介绍了Java中ClassLoader,小编现在分享给大家,供广大互联网技能从业者学习和参考。文章包含3030字,纯文字阅读大概需要5分钟。
内容图文
ClassLoader:类加载器。Java中所有的类都通过类加载器j进行加载,包含几种加载器:
- BootStrapClassLoader 使用C++编写属于Java的JVM层面。用于加载核心类库(lib)下的类库
- ExtensionClassLoader 用于加载Java lib/ext下的类库
- ApplicationClassLoader 用于加载classPath下的类库
ApplicationClassLoader的parent是Extension‘ClassLoader,ExtensionClassLoader的parent是BootStrapClassLoader。我们编写任意一个类AA,使用
System.out.println(AA.class.getClassLoader());
得到如下结果:
获取的是Lancher中的类,再使用
System.out.println(AA.class.getClassLoader().getParent());
得到如下结果
再使用
System.out.println(AA.class.getClassLoader().getParent().getParent());
得到的结果便是null了。
调用对象的getClass()方法是获取当前对象类的类型,该部分数据存储在方法区中,getClass().getClassLoader()方法是获取当前类型的类加载器。由于Java中所有类都通过类加载器加载到jvm中,且各个类加载器存在父子关系,子知道父的存在,父不知道子的存在,由于此不同子之间加载的类型是无法互相访问的(虽然都在方法区中),正是因为这样,通过当前类的加载器加载资源能够保证是同一个类加载器加载的。
InputStream resourceAsStream = AA.class.getClassLoader().getResourceAsStream("aa.txt");
JVM加载一个类时由BootStrapClassLoader首先进行查找加载,找不到时再有其子类ExtensionClassLoader查找加载,再找不到时由ApplicationClassLoader查找加载。这也就是“双亲委派机制”。
2.线程中的ClassLoader
每个运行中的线程都有成员ContextClassLoader线程上下文ClassLoader,用于在运行时动态加载其它类。通过
ClassLoader contextClassLoader = Thread.currentThread().getContextClassLoader();
可以获取当前运行线程的上下文ClassLoader。通过
Thread.currentThread().setContextClassLoader(new ClassLoader() { @Override public Class<?> loadClass(String name) throws ClassNotFoundException { return super.loadClass(name); } });
可以设置当前线程的ContextClassLoader
事实上所有Java程序都运行在线程中,若一个程序没有通过上述方法设置过ContextClassLoader,对于一般的jJava类下面两个方法获取的ClassLoader一般是同一个:
this.getClass().getClassLoader();
Thread.currentThread().getContextClassLoader();
上述两个方法区别:
第一个得到的是静态的ClassLoader,表明类的加载者
第二个得到的是动态的ClassLoader,表明当前线程。对于单例模式的类、静态的类载入一次后可能被其它多个线程调用,对于这些类,载入的ClassLoader和执行的线程的ClassLoader通常不同。
3.web应用中ClassLoader
以tomcat中webapp的ClassLoader来说,这类Class Loader与之前说过的机制略有不同,web应用线程会尝试自己加载(ContextPath/web-inf/....)中的类,若是加载不到,再请求父加载器加载。对于webapp线程,他的contextCloassloader是WebAppClassLoader,对于tomcat Server线程,他的ContextClassLoader是catalinaClassLoader。除了上述获取动态ClassLoader和获取静态ClassLoader外还可通过:
ClassLoader.getSystemClassLoader();
获取系统入口点所使用的ClassLoader。此类SystemClassLoader与根ClassLoader不同,JVM下SystemClassLoader通常为AppClassLoader。
ClassLoader可广泛用于资源载入层面,对于类资源,类可通过new,文件可进行IO。
类资源:
1.Class clazz=Class.forName("com.dabai.AA"); AA aa=(AA)clazz.newInstance(): 2.AA aa=new AA(); 3.ClassLoader cl; Class clazz=cl.loadClass("com.dabai.AA"); AA aa=clazz.newInstance();
文件资源:
假设AA类想要读取 com/dabai/conf/ 下文件conf.properties,我们可以通过绝对路径和相对路径读取,绝对路径自然是包括磁盘符的,相对路径的值是相对ClassLoader。将ClassLoader视为一棵树,相对与该ClassLoader路径后的资源都能被加载到
InputStream resourceAsStream3 = Thread.currentThread().getContextClassLoader().getResourceAsStream("com/dabai/conf/conf.properties");
获取文件URL绝对路径:
URL resource = BB.class.getClassLoader().getResource("com/dabai/Test/conf/conf.properties"); System.out.println(resource);
Java中getResource()会进入到ClassLoader getResource()中,通过main方法启动时,当前ClassLoader就是AppClassLoader,其parent就是ExtensionClassLoader,再其parent就是BootStrapClassLoader。当BootStrapResource都无法找到对应资源时,就从findResource(name)中将返回值返回。
原文:https://www.cnblogs.com/notably/p/12977566.html
内容总结
以上是互联网集市为您收集整理的Java中ClassLoader全部内容,希望文章能够帮你解决Java中ClassLoader所遇到的程序开发问题。 如果觉得互联网集市技术教程内容还不错,欢迎将互联网集市网站推荐给程序员好友。
内容备注
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 gblab@vip.qq.com 举报,一经查实,本站将立刻删除。
内容手机端
扫描二维码推送至手机访问。