ClassLoader(java 与 android 对比)

ClassLoader(java 与 android 的区别)

Java ClassLoader

JVM主要有三类ClassLoader:Bootstrap、Extention、Application,该三类ClassLoader从上到下是分级(hierarchy)结构,遵循代理模型(Delegation Model)。

  1. Bootstrap ClassLoader:也称为primordial(root) class loader。主要是负责装载jre/lib下的jar文件,当然,你也可以通过-Xbootclasspath参数定义。该ClassLoader不能被Java代码实例化,因为它是JVM本身的一部分。

  2. Extention ClassLoader:该ClassLoader是Bootstrap classLoader的子class loader。它主要负责加载jre/lib/ext/下的所有jar文件。只要jar包放置这个位置,就会被虚拟机加载。一个常见的、类似的问题是,你将mysql的低版本驱动不小心放置在这儿,但你的Web应用程序的lib下有一个新的jdbc驱动,但怎么都报错,譬如不支持JDBC2.0的 DataSource,这时你就要当心你的新jdbc可能并没有被加载。这就是ClassLoader的delegate现象。常见的有log4j、 common-log、dbcp会出现问题,因为它们很容易被人塞到这个ext目录,或是Tomcat下的common/lib目录。

  3. Application ClassLoader:也称为System ClassLoaer。它负责加载CLASSPATH环境变量下的classes。缺省情况下,它是用户创建的任何ClassLoader的父 ClassLoader,我们创建的standalone应用的main class缺省情况下也是由它加载(通过Thread.currentThread().getContextClassLoader()查看)。

我们实际开发中,用ClassLoader更多时候是用其加载classpath下的资源,特别是配置文件,如ClassLoader.getResource(),比FileInputStream直接。

Android ClassLoader

我们重点关注与我们热更新相关的PathClassLoaderDexClassLoader

  • PathClassLoader只能加载已经安装到Android系统中的apk文件(/data/app目录),是Android默认使用的类加载器。
  • DexClassLoader可以加载任意目录下的dex/jar/apk/zip文件,比PathClassLoader更灵活,是实现热修复的重点。

双亲委托模式

采取双亲委派模式主要有两点好处:

  • 避免重复加载,如果已经加载过一次Class,就不需要再次加载,而是先从缓存中直接读取。
  • 更加安全,如果不使用双亲委托模式,就可以自定义一个String类来替代系统的String类,这显然会造成安全隐患,采用双亲委托模式会使得系统的String类在Java虚拟机启动时就被加载,也就无法自定义String类来替代系统的String类,除非我们修改类加载器搜索类的默认算法。还有一点,只有两个类名一致并且被同一个类加载器加载的类,Java虚拟机才会认为它们是同一个类。

参考 https://blog.csdn.net/zly921112/article/details/83417774 //android classloader

你可能感兴趣的:(Android进阶)