標籤:
在 Android 開發中,有一個之前很少聽說,最近偶爾江湖傳聞聽到過的問題,就是 65k 問題。什麼是65k問題呢?其實很簡單,就是 Android 有個限制,你的每個 App 中函數最多隻能有 65536 個。
這個限制其實是這樣的,因為在編譯成 Dalvik 位元組碼,也就是把你的 Class 們產生打包到一個 classes.dex 中去的時候呢,編譯器會給你的 App 中所有的函數方法指定一個 ID, 然後每一個 classes.dex 中 ID 的範圍是 [0, 0xffff] 。 所以,你懂的,就有了那麼一個 65k 的問題。
當然大部分應用程式裡路上是不會遇到這個問題的,畢竟 65k 個函數也很多了,但是考慮到現在各種引入 SDK,而且尤其是大公司的程式往往會有很多匪夷所思的功能,最後代碼越來越臃腫,指不定哪天就遇到了。不過還好,這個問題也不難解決,Google官方已經給出瞭解決方案:
multidex support library
簡單翻譯下,原理就是編譯的時候不再是單純編譯到一個 Dex 檔案中去,而是切分成多個 Dex 檔案。這樣每個檔案都允許 65536 個函數,肯定是夠用了的。下面說下具體的操作。
首先就是匯入這個庫,這個 Eclipse 和 Android Studio 不太一樣,但是具體就不說了,因為太常見了。不過如果用的是新版本的 Android Studio 似乎已經無需匯入這個庫,貌似 IDE 直接支援了。只需要把設定檔中的 multiDexEnabled 設定成 true 就可以了,大概就是下面這個樣子:
defaultConfig { applicationId "com.example.hecun.myapplication" minSdkVersion 15 targetSdkVersion 23 versionCode 1 versionName "1.0" multiDexEnabled true }
然後就是讓你的 Application 類繼承自 MultiDexApplication 這個類 ,例如:
public class MyApplication extends MultiDexApplication { @Override public void onCreate() { super.onCreate(); }}
假如不方便修改繼承(比如已經繼承了其他的封裝了的 Application)那麼久稍微複雜一點,重載一下attachBaseContext,代碼如下:
public class MyApplication extends MultiDexApplication { @Override public void onCreate() { super.onCreate(); } @Override protected void attachBaseContext(Context base) { super.attachBaseContext(base); MultiDex.install(this); }}
至於為什麼重載attachBaseContext方法本人不是很明白,為什麼不直接寫在onCreate方法中,只是知道Application中方法的執行順序如下
還有一種情況就是沒有繼承過 Application 類怎麼辦?這種最方便,開啟你的 AndroidMainfest 檔案,在 application tag 中加入這個:
android:name="android.support.multidex.MultiDexApplication"
到此,問題算是解決了。但是這並不完美,在 Android 5.0之前,你還需要保證你的 Activity , Service等等基本上 Dalvik需要直接找你的東西都放在第一個 dex 中,否則你的 App 就會掛掉。這部分內容說起來比較複雜,我建議直接去看 Google 官方的說明,Building Apps with Over 65K Methods 。當然,如果你的程式只支援 Android 5.0 以後的機器,那就不用擔心了,因為 ART 會把多個 dex 合并成一個 oat 檔案,就不存在找不到的問題了。
解決傳說中的 Android 65k 問題