天天看點

android 64K(65k)問題解決辦法

1.問題顯示:

舊版編譯時出現:

Conversion to Dalvik format failed:

Unable to execute dex:method ID not in [0,0xffffff]:65536

新版編譯出現:

trouble writing output:

Too many field references :xxxx;max is 65536

2.原因:

android Dalvik 執行的由class編譯後的.dex檔案檔案規定了單個.dex 檔案最多能引用65536個方法,此問題描述為64K(65536/1024),或者65K(65536/1000),導緻的編譯錯誤提示

3.處理方式:

1. 盡量避免,遏制在搖籃中(畢竟分包是會影響性能的)

dex檔案的來字所有的class檔案,包含自身的方法,還有系統自帶的方法和第三方開源庫,盡可能的去減少不用的函數,不要為了小功能而引入大架構,小功能可以自己去實作,或者在開源庫中提取需要的方法,這也是我們需要解讀開源的一方面,提取所需,避免大炮打蒼蠅,方法盡量複用

2.使用Progurad 混淆來去掉無用的代碼,在Release版本中是能ProGuard

3.分包處理

   當項目過大無可避免的時候,隻能做手術了,把dex檔案分成多個包來處理,每個包小于64方法

  通過使用系統自帶的MulitDex來分包使能分包方式,

  1.首先引入它的庫和其他第三方庫一樣添加

  compile 'com.android.support:multidex:1.0.1' 

  2. 使能 multidex 的支援

 defaultConfig{

   minSdkVersion 18

   targetSdkVersion 23

   .........

 //使能 multidex 的支援

  multiDexEnabled true

}

3.在Application中的attachBaseContext方法中方法中初始

如果沒有定義Application,則定義一個繼承MultiDexApplicaon的類,重寫onCreate,調用下父類的該方法即可

@Override
protected void attachBaseContext(Context base) {
    super.attachBaseContext(base);
    MultiDex.install(this)
}
           

  最後注意:

  添加了分包處理可能出現的問題:

 1.因為多個dex,安裝可能導緻ANR

 2.4.0之前的版本可能出現啟動失敗(不過現在該系統使用的比例很小了)

 3.大額的記憶體申請配置設定時可能出現crash,因為加載堆記憶體的大小被系統寫死了,android 2.3 以下3M,2.3 5M,4.0 16,5.0由于是ART虛拟機不考慮該問題

4.分包後出現,主從dex檔案包(一個主dex,1個或多個從dex),應用啟動所需要的類必須放在主dex包中不然會出現NoClassDefFoundError錯誤,雖然大多時候,不需要關系,系統會自動幫我們把需要的類添加到主dex包中,但是對于第三依賴庫需要還需要依賴其他的庫的話,比如反射用的類,或者NDK代碼用的類,如果在啟動就需要用到那麼就需要放到主包中

5.編譯建構打包時因為要計算方法,分包處理等,是以很慢,

  處理方式

 調試時在建構時選擇5.0以上系統建構,因為該系統是ART虛拟機,直接生成一個oat檔案,而不是多個dex合并加載,釋出版時   改為支援的最低版本

 android{

  productFlavors{

            dev{

             minSdkVersion 21

            }

            prod{

             minSdkVersion 14//app實際的minSdkVersion

             }

  }

}