アウトライン
通常、ユーザーは特にないWIFIの場合には、より大きなプログラムをダウンロードすることを望んでいません。あなたのパッケージが小さい場合、ユーザーはまだ下の経験をダウンロードしてインストールして喜んでいます。今のApp出会いで利用可能な特定の要件は、通常、ユーザーが経験にアプリが喜んでダウンロードできるようにする方法、たくさんのお金を持っていますか?小さいインストールパッケージは、WIFI、ダウンロード速度のインストールの場合には、経験を起動します。モバイルネットワークの場合に、より小さなパッケージサイズ、大きいユーザがインストールされている可能性。そのため、インストールパッケージのサイズは、ユーザーのコンバージョン率に大きな影響を与えています。その後、実際には、パッケージサイズの最適化の仕事上の私の経験の一部を共有し。
APKファイルの構造
それは、Android APKインストールファイルのサイズを最適化することであるので、主な必要性は、APKファイルの下の構造を理解します。APKファイルはAndroidStudioは明らかにAPKファイルのコンポーネントを見ることができますドラッグ。APKは、主に以下のコンポーネントで構成されます。
- INF-META /:メインのファイルフォルダがCERT.SFとCERT.RSAシグネチャファイルだけでなく、マニフェストファイルが含まれているMANIFEST.MF
- 資産は、/:AssetManagerを取得するためにプログラム内のオブジェクトによってこのフォルダには、アプリのファイルの主な資産が含まれています
- RES /:メインフォルダにはファイルがresources.arscにコンパイルされていない含まれています
- libに/:ライブラリは、このようなarmeabi、armeabi-v7a、arm64-などの一部のプラットフォーム、含まれているので、このフォルダ v8a、x86の、x86_64版、およびMIPSを。
- resources.arsc:このファイルは、コンパイル済みのリソースを主に保たれています。RES /値ディレクトリ下のファイルの内容の主記憶装置、それがバイナリ形式にコンパイルディレクトリ(文字列、スタイル)のXML内容を抽出するパッケージツール。
- classes.dex:このファイルは、主に含まれているクラスファイルは、のDalvik / ART仮想マシンDEXフォーマットを理解することができます
- AndroidManifest.xml:AndroidのバイナリXML形式を使用してAndroidのマニフェスト文書ファイルの主コア。
最適化の方法
実際には、2つのコアコンテンツ、写真やコードリソースのAPK。そのため、主に二つの側面からのパケット最適化のボリューム。このようなチェックなど、assets
未使用のリソースディレクトリがあるかどうか。一般的にはめったに主に、資産のいくつかの役に立たないリソースディレクトリを入れていないサードパーティのSDKを(このような高いドイツ語、Baiduのマップ、などなど)を統合するときなど、画像、オーディオファイル、それにいくつかのリソースを配置する必要があり、プロジェクト、UIインターフェイススタイルの反復では、これまで以上に施さ大きな変化、非常に多くの絵の前にリソースが使用できなくなりますので、前にres
我々はクリーンアップしませんでした、写真のディレクトリをたくさん存在しない可能性がありますフォルダのリソースの中で最も重要な使用。絵に加えて、そのclasses.dex
ファイル、および当社独自のビジネスコードの一般的なプログラムは、主にサードパーティのライブラリの多数の使用、およびいくつかのモジュールは、同社の他のチームを統合し、パッケージサイズに大きな影響を持っていない、でしこれらのモジュールそれはあまり私たちは、コードやリソースを使用するよりも多く含まれています。
最適化する前に、インストールパッケージのサイズダウン、私はプロジェクトをやって表示するには73437キロバイト(71.7メガバイト)で、善を行うには、コントラストを最適化するために戻って、振幅の特定の最適化を見ています。
AndroidStudioで未使用のリソースを削除します
手動で削除したリソースには2つの利点がある:一つは、他のソースコードの量を減らすことです、インストールパッケージの量を減らすことです。
私たちはAndroidStudioでの未使用のリソースを見つけるのに役立つ2つの方法があります。
-
分析- >コードを点検して以下のように、実際には、糸くずのツールで結果を実行して、私たちは資源の絵に加えて、未使用のリソースを見つけるのに役立つだけでなく、コード内に存在する潜在的な問題を見つけるために私を助けるために:
-
Shiftキーをダブルクリックし、未使用のリソースを削除し入力し、Enterキーを押します。上記のアプローチによる未使用のリソースだけでなく、検出コードので、時間のかかる操作を識別するだけでなく。あなただけの未使用のリソースを検索したい場合は、ダブルクリックのシフトに彼らが結果は同じである検出方法を使用することができます。
上記のツールは、プロセスの使用に2つのピットを持っています:
-
リソースの使用は、それはまだ何も言及を報告されていません。そのような描画可能xmlファイルなどの一部のリソース、
-
また、プロジェクトがButterKnifeを使用している場合、R2は、IDによって適用され、レイアウトIDの多くを削除し、ツールがこれを検出することはできません
私たちはめったにアイコン描画可能ディレクトリを入れていないのでので、描画可能ディレクトリ内のリソースのために、私たちは、元に戻すにはgitできます。IDレイアウトの宣言が削除されたために、私たちは、フォルダを元に戻すレイアウトすることができます。
以上の動作により、成功裏に2.3Mパケットの量を減らします:
オペレーティング | ボリューム | 削減 |
---|---|---|
最適化の前に | 73437キロバイト(71.7メガバイト) | - |
コードを点検 | 71054キロバイト(69.3メガバイト) | 2383キロバイト(2.3M) |
プロセス内の未使用のリソースを手動で除去では、我々は別の問題を発見しました。今、私たちはプロジェクトのモジュールの数十をモジュラープロジェクトを持っている、モジュールは、必ずしもシステムのデフォルトic_launcherアイコン、デフォルトで生成された新しいモジュール、および私たちのプロジェクトの名前に変更したアイコンがたくさん含まれていapp_icon
ic_launcherではないの内側にあります、使用。8つのフォルダのic_launcher上の各モジュールの下で:
drawable
-> ic_launcher_background.xml
drawable-v24
-> ic_launcher_foreground.xml
mipmap-anydpi-v26
-> ic_launcher.xml
-> ic_launcher_round.xml
mipmap-hdpi
-> ic_launcher.png
-> ic_launcher_round.png
mipmap-mdpi
-> ic_launcher.png
-> ic_launcher_round.png
mipmap-xhdpi
-> ic_launcher.png
-> ic_launcher_round.png
mipmap-xxhdpi
-> ic_launcher.png
-> ic_launcher_round.png
mipmap-xxxhdpi
-> ic_launcher.png
-> ic_launcher_round.png
発表時点では必要ありませんが、我々はマニフェストデバッグを持っているし、マニフェストを解放し、その後、マークまたはライブラリアプリケーションによって判断され、一般的に、個別のコンポーネントを実行する必要があるかもしれませんが、時々、モジュールは、ランチャー必要になることがあります。実際に、それはまた、このデバッグの放出を達成するために他の方法で使用することができる(モジュール缶コート工学プロジェクトの層、プロジェクトは、アプリケーションとして実行することができ、このモジュールを含みます)。このように、モジュールは、アプリケーションの存在を必要としない、それがランチャーアイコンを必要としません。
実際には、これは開発者がランチャーリソースAARをたくさん見つけるでしょう、例えば、我々は、CTRL +シフト+ Rの検索ic_launcherによって、ライブラリ内の他の部署の多くに依存して、問題を無視することは非常に簡単でもあります。そして、さらにいくつかの非標準的なサードパーティ製のオープンソースのライブラリも、これらの問題。
オペレーティング | ボリューム | 削減 |
---|---|---|
最適化の前に | 73437キロバイト(71.7メガバイト) | - |
コードを点検 | 71054キロバイト(69.3メガバイト) | 2383キロバイト(2.3M) |
ランチャーを削除します | 71035キロバイト(69.3メガバイト) | 19キロバイト |
非常に多くのランチャーは、画像を削除なぜ、なぜAPKサイズは、19キロバイトを減少させますか?(どのような特定の少ない場所で、以前のAPKの機能と比較することによって比較することができます)。
だけで同じ名前のリソースファイルを使用し、最終生成APKの時以来、私たちは、同じモジュールの複数のパスが同じ名前の存在について、優先パッケージになり(適度な最適化、一つだけが存在するであろうあなたは見ることができます公式ドキュメントを)。しかし、我々はいくつかのゴミプロジェクトのリソースをクリーンアップする必要があります。
オープンシュリンクリソース
実際には、我々のプロジェクトのアプリ/ build.gradleシュリンクリソースにオープンで構成されました:
minifyEnabled true
shrinkResources true
私たちは、プログラムのアイコン名を使用ic_launcherを使用していないが、app_icon、私たちは私たちのAPK APKもic_launcherアイコン名のic_launcherリソースは、プログラムで使用すべきではない見つかり分析を分析し合格し、なぜそれを縮小しませんか?二つの可能性があります。
- ic_launcherファイルを使用して隠されたどこかにあります。
- 力ではないシュリンク
プロジェクトのシュリンクが発効していない見てみましょう。私は(も間接的ic_launcherでどこかを使用する手順を説明し)、ファイルが記述されている場合シュリンクシュリンクが有効である場合、再パッケージ化され、行くプロジェクトに新しいリソース(abc.webp)を入れ、そうでない場合はそれが有効に縮小することはありません設定上で説明シュリンク、あなたはそれを有効にしましょうする方法を見つけることができます。
新世代のAPKはAPKが開いて分析し、新しく追加された見つかったファイルabc.webp
のファイルがまだ存在します。
説明は効果を縮小しません。明らかにそれはminifyEnabled、shrinkResources、なぜ力でまだ設定されています。
検索した後、元はProGuardのファイルに収縮しないように設定されています。
-dontshrink
この行は、コメント、その後、再パッケージ化し、見つかっ減少3.37メガバイト
オペレーティング | ボリューム | 削減 |
---|---|---|
最適化の前に | 73437キロバイト(71.7メガバイト) | - |
コードを点検 | 71054キロバイト(69.3メガバイト) | 2383キロバイト(2.3M) |
ランチャーを削除します | 71035キロバイト(69.3メガバイト) | 19キロバイト |
ShrinkResources | 67576キロバイト(65.9メガバイト) | 3459キロバイト(3.37M) |
shrinkModeは主に二つある:安全で、厳格な、デフォルトのモードは安全です。
あなたは、可能なres/raw/keep.xml
shrinkModeファイルを設定さ:
<?xml version="1.0" encoding="utf-8"?>
<resources xmlns:tools="http://schemas.android.com/tools"
tools:shrinkMode="safe"/>
あなたはシュリンクリソースを開くとshrinkModeが厳格strictモードを=とき、shrinkMode =安全で、パックの時間は、そのような)(resources.getIdentifierリソースへのアクセスの仕方などによって参照することができるこれらのリソースを、見つけるためのイニシアチブを取るとき、リソースは、削減されることはありませんリソースが減少されることはありません。
私は実験をしていた、私たちは、リソースがシュリンクある場合ことを発見し、それはまだAPK中かもしれませんが、リソースの量が非常に小さくなる。
あなたはshrinkModeの安全を設定した場合の検出はそれほど正確ではないかもしれないので、保存されるようにも使用されていないかもしれません。
あなたはshrinkModeは、厳密にあなたはリソースが追いつくかresources.getIdentifier(A)を介して取得する必要があり、この時間を設定することができます。あなたにはkeep.xmlに保つためのファイルを設定できます。
<?xml version="1.0" encoding="utf-8"?>
<resources xmlns:tools="http://schemas.android.com/tools"
tools:shrinkMode="strict"
tools:keep="@drawable/ic_get_by_identifier"/>
関連する知識の詳細混乱、あなたが見ることができますAndroidAllを
WEBPにターンをPNG形式
Android4.0はWEBPをサポートするために始めたが、唯一のAndroid4.3、ロスレスWEBPで透明度をサポートしています。あなたのアプリが4.3の最小値をサポートしているのであれば、あなたはPNGの代わりにWEBPを使用することができます。
AndroidStudioでは、変換中にキーのサポート、あなたは質量比のトランスコーディングを選択することができます、また代わりに、元のPNGよりも大きいWEBPで、スキップすることができるかどうかに目を向けるように選択することができます。
オペレーティング | ボリューム | 削減 |
---|---|---|
最適化の前に | 73437キロバイト(71.7メガバイト) | - |
コードを点検 | 71054キロバイト(69.3メガバイト) | 2383キロバイト(2.3M) |
ランチャーを削除します | 71035キロバイト(69.3メガバイト) | 19キロバイト |
ShrinkResources | 67576キロバイト(65.9メガバイト) | 3459キロバイト(3.37M) |
Png2webp | 64505キロバイト(62.9M) | 3071キロバイト(3M) |
R8を有効にします
私たちは閉じられますので、R8は、非常に安定していないの前にいるので。今AndroidStudio 3.6は、我々はそれを開きます。
android.enableR8=true
公式サイトはR8 ProGuardのサポート、まだいくつかの問題ルールファイルを既存ますが、実際の使用で言ったものの、再びリリースパッケージを再生し、いくつかの混乱の設定の問題を解決し、減少0.9Mを見つけました:
オペレーティング | ボリューム | 削減 |
---|---|---|
最適化の前に | 73437キロバイト(71.7メガバイト) | - |
コードを点検 | 71054キロバイト(69.3メガバイト) | 2383キロバイト(2.3M) |
ランチャーを削除します | 71035キロバイト(69.3メガバイト) | 19キロバイト |
ShrinkResources | 67576キロバイト(65.9メガバイト) | 3459キロバイト(3.37M) |
Png2webp | 64505キロバイト(62.9M) | 3071キロバイト(3M) |
R8 | 63506キロバイト(62M) | 999キロバイト(0.97M) |
上記通常モードR8、R8と同様にフルモードですが、またいくつかの追加の最適化操作、R8全開モードを行う、まだ実験的な性質です。
android.enableR8.fullMode=true
リリースパッケージを演奏Reおよび減少0.16Mを見つけました:
オペレーティング | ボリューム | 削減 |
---|---|---|
最適化の前に | 73437キロバイト(71.7メガバイト) | - |
コードを点検 | 71054キロバイト(69.3メガバイト) | 2383キロバイト(2.3M) |
ランチャーを削除します | 71035キロバイト(69.3メガバイト) | 19キロバイト |
ShrinkResources | 67576キロバイト(65.9メガバイト) | 3459キロバイト(3.37M) |
Png2webp | 64505キロバイト(62.9M) | 3071キロバイト(3M) |
R8 | 63506キロバイト(62M) | 999キロバイト(0.97M) |
R8 FullMode | 63333キロバイト(61.8M) | 173キロバイト(0.16M) |
代わりに、カスタムビューによってアイコンの
我々はまた、カスタムビューによって、このような注文状況、還付の状態など、いくつかのステータスアイコンを置き換えることができます。次のとおりです。
これらのアイコンは、カスタムビューを使用して行うことができます似ている、あなたは絵の多くのリソースを減らすことができます。状態多くの場合は、ステータスアイコンの多くを必要とする、国際支援あれば、それはまた、各国の対応するステータスアイコンを生成する必要があります。
交換用の状態カスタムビューアイコンの後、縮小パッケージサイズ0.366M:
オペレーティング | ボリューム | 削減 |
---|---|---|
最適化の前に | 73437キロバイト(71.7メガバイト) | - |
コードを点検 | 71054キロバイト(69.3メガバイト) | 2383キロバイト(2.3M) |
ランチャーを削除します | 71035キロバイト(69.3メガバイト) | 19キロバイト |
ShrinkResources | 67576キロバイト(65.9メガバイト) | 3459キロバイト(3.37M) |
Png2webp | 64505キロバイト(62.9M) | 3071キロバイト(3M) |
R8 | 63506キロバイト(62M) | 999キロバイト(0.97M) |
R8 FullMode | 63333キロバイト(61.8M) | 173キロバイト(0.16M) |
CustomView | 62958キロバイト(61.4M) | 173キロバイト(0.36M) |
使用AndResGuard
マイクロチャネル使用AndResGuardは、リソース名の変更は、ABCのようにすべての方法であることを、リソースパスおよびリソース名にリソースに関する混乱することができます。これは、大幅にキャラクターの名前が占めるスペースを減らすことができます。
特に、同じ名前を防止するために、モジュラーリソースの後、我々はこのようにさえなりましたリソースの名前につながる、モジュールのプレフィックスのリソースを追加します。AndResGuardを使用している場合、getIdentifierの方法を介して利用可能なプログラムのリソースは、必ずホワイトリストに、このプログラムでグローバル検索することも可能。
通过 AndResGuard 混淆后,包体积减少了 3.54M:
操作 | 体积 | 减少 |
---|---|---|
优化前 | 73437KB(71.7MB) | - |
Inspect Code | 71054KB(69.3MB) | 2383KB(2.3M) |
Remove Launcher | 71035KB(69.3MB) | 19KB |
ShrinkResources | 67576KB(65.9MB) | 3459KB(3.37M) |
Png2webp | 64505KB(62.9M) | 3071KB(3M) |
R8 | 63506KB(62M) | 999KB(0.97M) |
R8 FullMode | 63333KB(61.8M) | 173KB(0.16M) |
CustomView | 62958KB(61.4M) | 173KB(0.36M) |
AndResGuard | 59323KB(57.9M) | 3635KB(3.54M) |
so 文件
在主流的手机CPU架构都是 ARM,基本上只要支持这一种架构就可以了。更多关于这方面的知识可以查看 Android NDK ~ 基础入门指南
我们来看下市面上主流的 app 支付宝和微信的 CPU 架构:
armeabi-v7a 是向下兼容 armeabi,arm64-v8a 能兼容 armeabi-v7a 和 armeabi
我们项目中也是只支持一种 armeabi-v7a 架构,减少 so 文件体积大小
release {
ndk {
abiFilters 'armeabi-v7a'
}
//...
}
小结
到此,就介绍完了我这次包体积优化相关内容了,差不多了减少了 20% 的包体积大小。当然优化是无止尽的,除了上面的一些优化手段还有 app Bundles 的方式(需要结合 Google Play 一起);还可以考虑通过 BackgroundLibrary 替换程序中大量的 shape、selector 文件,减少包体积,但是该库对性能有一定的影响,所以我还没有使用,后面可以考虑是否还有更好的方案;还可以找出程序中重复的图片(图片内容一致,名字不同);当然还有插件化,插件也需要瘦身,减少下发消耗的流量。
私に関わる別のソース記事AndroidAllのGitHubリポジトリ。倉庫に加えて性能优化
、だけでなく、Androidのプログラマは技術スタックを習得する必要がある、など:アプリケーションアーキテクチャ、デザインパターン、パフォーマンスの最適化、データ構造、アルゴリズム、Kotlin、フラッター、NDK、人気のオープンソースのフレームワークルータ、RxJava、グライド、LeakCanary、 Dagger2、 レトロフィット、OkHttp、ButterKnife、分析ルータの原則など、継続的に更新され、スターを歓迎しました。