Class.forName("xxx")调用过程

大兔子大兔子 提交于 2019-12-03 18:50:39

问题:java.lang.ClassNotFoundException


1.Class.forName("xxx")作用概述

    xxx:字符串,表示要装载的类名或者是驱动名字。

   Class.forName()的主要作用是将“xxx”表示的类装载到JAVA虚拟机中。

2.Class.forName("xxx")具体加载过程

    解决的问题:

  •          “xxx”表示类的字节码应该放在哪里?
  •         Class.forName("xxx")调用过程的相关的类、对象和系统环境?
  •         设计Class.forName("xxx")的意义?

2.1 Class.forName("xxx")寻找过程细节?

     这里主要解决前两个问题—— “xxx”表示类的字节码应该放在哪里?和Class.forName("xxx")调用过程的相关的类、对象和系统环境?

java.sql.DriverManager.registerDriver(new Driver());【1】

在这篇博文中,表示java.sql.DriverManager是在Class.forName("xxx")中的xxx类放入内存后,才静态注册驱动类。但是JVM如何将xxx放入内存呢?下面是Class类中forName()的源代码

    public static Class<?> forName(String className)
                throws ClassNotFoundException {
        return forName0(className, true, ClassLoader.getCallerClassLoader());
    }
 private static native Class<?> forName0(String name, boolean initialize,
                                            ClassLoader loader)
        throws ClassNotFoundException;


    public static Class<?> forName(String name, boolean initialize,
                                   ClassLoader loader)
        throws ClassNotFoundException
    {
        if (loader == null) {
            SecurityManager sm = System.getSecurityManager();
            if (sm != null) {
                ClassLoader ccl = ClassLoader.getCallerClassLoader();
                if (ccl != null) {
                    sm.checkPermission(
                        SecurityConstants.GET_CLASSLOADER_PERMISSION);
                }
            }
        }
        return forName0(name, initialize, loader);
    }
 
 

从上述的Class类的相关方法,可以看出forName()方法的实现还跟ClassLoader类有关。

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();
    }
这个是forName0(String,boolean,ClassLoader)中ClassLoader类调用的其自身的静态方法getCallerClassLoader()的实现代码。而实现代码中,又个Reflection类有关,调用了其静态方法getCallerClass(3)。那么,这个3是什么意思呢?无法查看源代码。


然后,百度了”getCallerClass(3)“,在一篇博文【2】中介绍了几种Classloader类,以及它们需要加载库的范围

  •     Bootstrap ClassLoader - GetClassLoader的返回值为Null,是JVM的C++源码, Ext ClassLoader 的Parent主要负责jdk_home/lib目录下的核心 api 或 -Xbootclasspath 选项指定的jar包装入工作
  •     System ClassLoader -  GetClassLoader返回值为SystemClassLoader. 主要负责java -classpath/-Djava.class.path所指的目录下的类与jar包装入工作
  •      Ext ClassLoader  - 是AppClassLoader 的Parent 返回Ext ClassLoader 主要负责jdk_home/lib/ext目录下的jar包或 -Djava.ext.dirs 指定目录下的jar包装入工作。
  •      App ClassLoader - 返回AppClassLoader。主要负责加载用户类
  •       Customer Class Loader  - 一般都继承App ClassLoader 用户自定义。



参考:

    http://blog.csdn.net/youlingqishi11/article/details/7395716

    http://blog.csdn.net/dianxer/article/details/6255823

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!