熱修復預備知識

前期預備知識

dex/class

  1. class文件結構解析
    • 什麼是class文件?java

      可以被jvm識別,加載並執行的文件格式android

    • 如何生成一個class文件算法

      • [x] 經過IDE自動幫咱們build
      • [x] 手動經過javac 去生成class文件
        PS: 如何制定jdk版本生成字節碼文件呢?—>javac -target 1.6 -source 1.6 HelloWorld.java
      • [x] 經過java命令去執行class文件
        java com.example.hostfit.Test ps: 執行時根據全類名來執行的
    • class文件的做用 記錄類文件的全部信息(記錄了this super 等關鍵字)緩存

    • class文件結構及格式(宏觀) class文件結構安全

      • 一種八位字節的二進制流文件
      • 各個數據按照順序緊密排列,無間隙
      • 每一個類或接口都單獨佔一個class文件
    • class文件弊端服務器

      • 內存佔用大,不適合移動端
      • 堆棧加載模式,加載速度慢
      • 文件IO操做多,類查找慢
  2. dex文件結構解析
    • 什麼是dex文件app

      被DVM虛擬機識別,加載並執行的文件格式jvm

    • 如何生成dex文件ide

      • [x] 經過IDE自動幫咱們build生成
      • [x] 手動經過dx命令去生成dex文件
        • javac -target 1.6 -source 1.6 Test.java 生成class文件。ps:指定1.6 版本爲了保證兼容
        • dx --dex --output=Test.dex com/example/hostfit/Test.class ps: 是根據全類名來找的
      • [x] 手動運行dex文件在手機上
        • 將dex文件push 到手機存儲卡中 adb push Test.dex '手機路徑(例如:/sdcard)'
        • dalvikvm -cp Test.dex com.example.hostfit.Test ps: 注意全類名
    • dex文件的做用ui

      記錄整個工程中全部類文件的信息。

    • dex文件結構、格式的詳解 dex文件結構

      • 一種八位字節的二進制流文件
      • 各個數據按照順序緊密排列,無間隙
      • 整個應用中全部的java源文件都放在一個dex文件中 ps: 不考慮android 官方提供的multidex
  3. class 與 dex 文件對比 class 與 dex異同
    • 本質上他們都是同樣的,dex文件從class文件演變而來
    • class文件存在許多冗餘信息(一個類就有一個常量池),而dex文件會去除冗餘,並進行整合

jvm/dvm/art 三種虛擬機

  1. java 虛擬機結構解析

    • jvm總體結構

    jvm 結構

    • java代碼的編譯和執行過程

      • 代碼編譯過程 編譯流程

      • 執行過程 加載流程 1. Loadding :類的信息從文件中獲取而且載入到JVM內存中 2. Verrifying: 檢查讀入的結構是否符合JVM規範的描述 3. Preparing: 分配一個結構用來存儲類信息 4. Resolving: 把這個類的常量池全部的符號引用改變成直接引用 5. Initializing: 執行靜態初始化程序,把靜態變量初始化指定的值

    • Java 內存管理

      • Java 棧區

        用來存放Java方法執行的全部數據 ps: method call-> a -> b - c;棧區由棧幀組成,一個棧幀表明一個方法的執行。

        那什麼是棧幀呢?每個方法從調用到執行完成就對應一個棧幀在虛擬機中入棧到出棧。每個棧幀包括局部變量表、棧操做數、動態連接、方法出口。例如(StackOverFlow異常)

        本地方法棧:和Java方法棧一模一樣,只不過本地方法棧是專門爲Native方法服務的

      • 方法區

        存儲被虛擬機加載的類信息,常量,靜態變量,便是編譯器後等數據,用於佔據內存的

      • Java堆

        全部經過New建立的對象的內存都在堆中分配,是虛擬機中最大的一塊內存,是GC 要回收的部分

        Java 堆區內存

        1. Young Generation : 剛剛New出來的對象
        2. Old Generation: 當Young Generation 中內存空間不足的時候,就會將Young Generation 中的對象按照必定的算法、規則等存放到Old Generation, 這樣 Young Generation 就能夠繼續分配內存,當二者都沒有剩餘的空間的時候,就會發生OOM異常,垃圾回收器主要針對這兩塊內存區域,
        3. Permanent Generation: Java8 已經移除

        特色:Young Old Generation 能夠動態分配,當咱們的服務器處理的是及時通信相關服務,就能夠將Young Generation內存區域調整大一些;當咱們不須要頻繁去建立對象的時候,能夠將Young Generation 內存區域調整小一些,這樣達到內存對象常駐的效果

    • Java 內存回收機制

      1. 垃圾回收算法

        • 引用計數算法

          缺點:互相循壞引用 ,兩個對象不可達,可是GC依然不會回收

        • 可達性算法

          Java 堆區內存

      2. 引用類型

        強引用、弱引用、軟引用、虛引用

      3. 如何回收垃圾

        • 標記-清除算法

          Java 堆區內存 優勢: 內存塊不須要進行對象移動,存活對象比較多的時候,高效; 缺點: 容易形成內存碎片,不利於後續對象的分配

        • 複製算法

          Java 堆區內存 優勢:存活的對象比較少,比較高效 缺點:成本須要一塊內存做爲交換空間

        • 標記-整理算法

          Java 堆區內存 優勢: 解決內存碎片問題 缺點: 成本較高一點

      4. 觸發回收機制

        • [x] Java虛擬機沒法再爲新的對象分配內存空間
        • [ ] 手動調用System.gc() 強烈不推薦
        • [x] 低優先級的GC線程,被Jvm 啓動了,執行GC
  2. Dalvik 與 jvm的不一樣

    • 執行的文件不一樣 一個是dex 一個是class文件
    • 類加載的系統(ClassLoader)與JVM的區別比較大
    • jvm 只能同時存在一個,DVM能夠同時存在多個
    • DVM 是基於寄存器的(運行更快),JVM 是基於棧的
  3. ART比Dalvik有哪些優點

    • DVM 使用的是JIT來將字節碼轉換成機器碼(每次運行),效率低
    • ART 是採用AOT的預編譯技術(安裝的時候就將字節碼轉換成機器碼存儲於介質中,不須要每次進行轉換),執行速度更快
    • ART 會佔用更多的應用安裝時間和存儲空間(以空間換時間)

class loader(Java Android)

類是如何加載到虛擬機的?

  1. Java 中的ClassLoader回顧

    Java ClassLoader 具體回顧 -> java代碼的編譯和執行過程

  2. Android中ClassLoader 做用詳解

    • Android ClassLoader的種類

      • BootsClassLoader

        用來加載Android framework層的一些dex文件

      • PathClassLoader

        用來加載已經安裝到系統中的apk文件中的dex文件

      • DexClassLoader

        用來加載指定目錄中dex文件

      • BaseDexClassLoader

        是PathClassLoader DexClassLoader 的父類

      一個App至少須要BootClassLoader 和PathClassLoader

    • Android ClassLoader 的特色

      • 雙親代理模型特色

        當前的classLoader去加載此類,若是當前此類已經被ClassLoader加載過就再也不加載,直接返回; 若是未加載,便會查詢它的Parents 是否加載過此類,若是加載過 就返回parents加載過的字節碼文件; 若是整個繼承線的都沒有加載過此類,便會子類真正的加載,提升類加載效率。這樣就會帶來如下兩個做用

      • 類加載的共享功能 一些FrameWork層級的類 ,一旦被頂層的classLoader加載過,那麼它就會緩存到內存裏面,之後任何地方用到,就不用從新加載了

      • 類加載的隔離功能 不一樣繼承路線上的ClassLoader 加載的類不是同一個類,避免開發者本身寫一代碼僞形成系統的類庫來訪問咱們系統可見成員變量。例如:系統層級的類通常初始化的時候就會加載,好比java.lang.String, 應用程序啓動以前就會被系統加載,若是在一個app裏面寫一個自定String 替換掉java.lang.String 會形成嚴重的安全問題。判斷是不是同一個類判斷,除了className packageName 另外還須要是同一個ClassLoader加載的。

    • ClassLoader 源碼 (加載流程)

      Java ClassLoader ClassLoader loadClass 首先判斷被本身或者雙親加載過,若是未加載過,調用BaseDexClassLoader 的findClass,調用DexPathList findClass ,而且完成將dex文件轉換成DexFile ,轉換成Elements, 遍歷數據,調用DexFile loadClassBinaryName - > native

  3. Android 中動態加載要點?

    • 有許多組件(Activity)類須要註冊才能使用
    • 資源動態加載複雜(註冊、兼容性)
    • 程序運行的時候須要一個上下文環境
相關文章
相關標籤/搜索