Android:这是一份全面 & 详细的 - 热修复 - 学习指南,含泪狂刷 Android 基础面试 118 题
#####1. 简介
#####2. 储备知识热补丁的原理主要基于: Android Dex 分包方案 & Android 的类加载机制(ClassLoader)所以,在讲热补丁的原理前,先了解上述 2 个储备知识 2.1 Android Dex 分包方案简介
示意图
2.2 Android 类加载机制(ClassLoader)简介
加载流程说明
示意图
注:若 2 个 Dex 文件中有重复的类,当加载时,则优先加载排序较前的 Dex 文件的类
若所需加载类 = class3,则最终加载的是排序较前的 De
x1 文件中的 class3
源码分析由于 具体实现类 PathClassLoader、DexClassLoader 都继承自 BaseDexClassLoader 类,所以此处主要讲解 BaseDexClassLoader 类中与类加载的相关方法 findClass()
/**
加载流程说明**/// 1. 传入需加载类的名字(classname)// 2. 通过 Dex 文件,寻找到所需类(findClass)// a. 按顺序遍历 ClassLoader 的所有 Dex 文件,即 集合 dexElements// b. 每遍历到 1 个 Dex 文件,则在该 Dex 文件中寻找所需加载的类// c. 若在该 Dex 文件找到该类,则返回;若找不到,则继续遍历下 1 个 Dex 文件// 3. 加载所需类
/**
BaseDexClassLoader 的 findClass()源码分析**/@Overrideprotected Class<?> findClass(String name) throws ClassNotFoundException {
// 从 pathList 对象对象中寻找->>分析 1Class clazz = pathList.findClass(name);
if (clazz == null) {throw new ClassNotFoundException(name);}
return clazz;}
/**
分析 1:DexPathList 的 findClass()源码分析**/public Class findClass(String name) {// 1. 按顺序遍历 ClassLoader 的所有 Dex 文件,即 集合 dexElementsfor (Element element : dexElements) {DexFile dex = element.dexFile;
// 2. 每遍历到 1 个 Dex 文件,则在该 Dex 文件中寻找所需加载的类 ->>分析 2if (dex != null) {Class clazz = dex.loadClassBinaryName(name, definingContext);// 3. 若在该 Dex 文件找到该类,则返回;若找不到,则继续遍历下 1 个 Dex 文件 if (clazz != null) {return clazz;}}}
return null;}
/**
分析 2:DexFile 的 loadClassBinaryName()源码分析**/public Class loadClassBinaryName(String name, ClassLoader loader) {return defineClass(name, loader, mCookie);}
评论