Class.forName(String className)使用哪个类加载器?
来源:互联网 发布:算法概念和特征 编辑:程序博客网 时间:2024/05/21 11:30
不看源码,以为Class.forName(String className)使用的是系统类加载器,看了源码才知道不是这么回事。
public static Class<?> forName(String className) throws ClassNotFoundException { return forName0(className, true, ClassLoader.getCallerClassLoader()); }通过 ClassLoader.getCallerClassLoader()获取类加载器:
// Returns the invoker's class loader, or null if none. // NOTE: This must always be invoked when there is exactly one intervening // frame from the core libraries on the stack between this method's // invocation and the desired invoker. static ClassLoader getCallerClassLoader() { // NOTE use of more generic Reflection.getCallerClass() Class caller = Reflection.getCallerClass(3); // This can be null if the VM is requesting it if (caller == null) { return null; } // Circumvent security check since this is package-private return caller.getClassLoader0(); }看第一行注释,返回的是调用者的类加载器。显然,调用者的类加载器不一定是系统类加载器,比如我们使用了自定义类加载器。看下面的例子:
User.java
package org.zzj;public class User {}UserService.java
package org.zzj;public class UserService {public void add() {try {System.out.println(Class.forName("org.zzj.User").getClassLoader());} catch (ClassNotFoundException e) {e.printStackTrace();}}}ClassForNameTest.java
package org.zzj;import java.io.IOException;import java.io.InputStream;import java.lang.reflect.Method;public class ClassForNameTest {public static void main(String[] args) throws Exception {System.out.println(Class.forName("org.zzj.User").getClassLoader());MyClassLoader classLoader = new MyClassLoader();Class<?> clazz = classLoader.loadClass("org.zzj.UserService");Method method = clazz.getMethod("add");method.invoke(clazz.newInstance());}}class MyClassLoader extends ClassLoader {@Overridepublic Class<?> loadClass(String name) throws ClassNotFoundException {String fileName = name.substring(name.lastIndexOf(".") + 1) + ".class";InputStream in = getClass().getResourceAsStream(fileName);if (in == null) {return super.loadClass(name);}byte[] b = null;try {b = new byte[in.available()];in.read(b);in.close();} catch (IOException e) {e.printStackTrace();}return defineClass(name, b, 0, b.length);}}输出:
sun.misc.Launcher$AppClassLoader@19821forg.zzj.MyClassLoader@14318bb两次加载使用的不是同一个类加载器,而是调用者的类加载器。
0 0
- Class.forName(String className)使用哪个类加载器?
- Class.forName(String className)使用哪个类加载器? 2015-01-08 20:56 2196人阅读 评论(0) 收藏 举报 分类: Java虚拟机(13) 版权
- Class.forName(String className) 实例化对象问题
- Java 编程下使用 Class.forName() 加载类
- 关于Class.forName(className).newInstance()的理解
- 关于Class.forName(className).newInstance()介绍
- 关于Class.forName(className).newInstance()介绍
- 关于Class.forName(className).newInstance()介绍
- 关于Class.forName(className).newInstance()介绍
- java中动态加载类 Class.forName
- Class.forName加载JDK类(Srtring)
- Java中的类加载和Class.forName()
- 类加载机制之Class.forName()
- JAVA反射机制,get.method()/ Class.forName(className)
- Class.forName(String )怎么用
- Class.forName的使用
- Class.forName()使用详解
- class.forname()的使用
- 有些东西,我们还不知道
- 使用hash方法切割文件
- java 练习------创建线程,获取线程对象及名称,线程状态
- windows7系统Prolific USB-to-Serial Comm Port问题
- Json语法解析
- Class.forName(String className)使用哪个类加载器?
- JSP一点总结
- 二分查找法
- apache2.2.22 嵌入式移植403访问权限问题(You don't have permission to access / on this server)
- 转角遇到大神
- webbrowser精华内容
- 四种遍历map的方法
- 正则表达式(整理)
- easyui中tree的父节点id获取