`

classloader举个例子

阅读更多
今天下午被一个同事问起,什么情况下需要用到ContextClassLoader

另一篇博客http://kyfxbl.iteye.com/blog/1900855已经介绍过了,这里就再举个更简单的例子

一个很常见的例子,是在JNDI里的。JNDI的入口类在rt.jar里,是由bootstrap classloader加载的;而JNDI的SPI实现类,则是由各厂商提供的,一般在classpath里,由app classloader加载

所以如果在JNDI的入口类里执行:
Class.forName("xxx.xxx.xxx");

就会抛ClassNotFoundException,要用这个方法才可以
public static Class<?> forName(String name, boolean initialize,  
                   ClassLoader loader)  
        throws ClassNotFoundException  

上面这个方法的第3个参数,就是从ContextClassLoader里来的,用
Thread.currentThread().getContextClassLoader();


下面再用一段代码模拟一下
public class Dong {

	public void call() {
		try {
			Class.forName("net.kyfxbl.test.cl.Target").newInstance();
		} catch (Exception exc) {
			exc.printStackTrace();
		}

	}

}

下面还有一个Target类,只是用来占位
public class Target {

}

最后是作为入口的main方法
public static void main(String[] args) {

		Dong dong = new Dong();
		dong.call();

	}

直接执行是没问题的

然后把Dong这个类打到jar包里,然后放到bootstrap classloader的加载路径里



然后编译会报错,因为bootstrap classloader加载的JAR包默认是不允许乱改的,可以强行去掉这个限制



然后再次执行main方法,就抛出了ClassNotFoundException。因为bootstrap是看不到classpath里的Target类的。同样的代码,在运行时却有不同的表现
  • 大小: 45.5 KB
  • 大小: 39.2 KB
分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics