日期:2014-05-20  浏览次数:20648 次

反射加载类 与 使用类加载器加载类有什么区别
方式一:反射加载
Class cl = Class.forName("classname"); 


方式二
使用ClassLoader
URLClassLoader loader = new URLClassLoader(urls);
Class cl = loader.loadClass("classname);



这两种方式加载类  有什么区别吗?  或者说有什么联系?

------解决方案--------------------
一样的,没有区别,类装载器装载是指定装载器,forname是使用当前类装载器装载。
------解决方案--------------------
一个是用在j2se项目上的,一个是用在Web项目上的,但是有时这两个都能用,用哪个都可以
------解决方案--------------------
引用:
引用:一样的,没有区别,类装载器装载是指定装载器,forname是使用当前类装载器装载。

就是说这两种方式是使用 ClassLoader 不同的实现类  去实现的。 对吗?

这个视情况而定,可以一样,也可以不一样,调用者选择而已
------解决方案--------------------
Class.forName是从指定的classloader中装载类,如果没有指定,也就是一个参数的时候,是从装载当前对象实例所在的classloader中装载类. 
      而ClassLoader的实例调用loadclass方法,是指从当前ClassLoader实例中调用类,而这个实例与装载当前所在类实例的Classloader也许不是同一个.


1.Class.forName返回的Class对象可以决定是否初始化。而ClassLoader.loadClass返回的类型绝对不会初始化,最多只会做连接操作。 
2.Class.forName可以决定由哪个classLoader来请求这个类型。而ClassLoader.loadClass是用当前的classLoader去请求。



ClassLoader 


bootstrap classloader(启动类加载器) 
>>这个ClassLoader在JVM运行的时候加载java核心的API以满足java程序最基本的需求,其中就包括用户定义的ClassLoader 


通过java程序实现的ClassLoader: 
>>ExtClassLoader : 这个ClassLoader是用来加载java的扩展API的,也就是/lib/ext中的类. 
>>AppClassLoader : 这个 ClassLoader是用来加载用户机器上CLASSPATH设置目录中的Class的,通常在没有指定ClassLoader的情况下,程序员自定义的类就由该ClassLoader进行加载. 


程序运行:  

当运行一个程序的时候,JVM启动,运行bootstrap classloader,该ClassLoader加载java核心API(ExtClassLoader和AppClassLoader也在此时被加载),然后调用ExtClassLoader加载扩展API,最后AppClassLoader加载CLASSPATH目录下定义的Class,这就是一个程序最基本的加载流程
------解决方案--------------------
Class.forname(classname)会初始化这个类,可能还要加载其它相关类。
ClassLoader.loader(classname)只是加载这个类
------解决方案--------------------
效果一样。至于底层如何不同,还真还细心去研究看看。
------解决方案--------------------
深入了解java虚拟机
------解决方案--------------------
深入java虚拟机第二版 这个书。