21、APK分析:APK Analyzer使用、分析APK组成、减少APK体积

APK 分析,说白了就是给你的安装包做一次「体检」。我刚开始做 Android 开发那会儿,APK 动不动就 50MB、80MB,用户下载意愿直线下降。后来 Google 推出了 APK Analyzer,这工具简直就是救星。今天我就带你把它用透。

APK Analyzer 怎么打开?

有两种方式进入这个工具:

  • 拖拽大法:直接把 .apk 或 .aab 文件拖到 Android Studio 的编辑器区域
  • 菜单路径:Build → Analyze APK… 然后选择你的 APK 文件

我个人习惯用拖拽,快。打开后你会看到一个分栏界面,左边是文件树,右边是详细信息。

核心功能一览:

  • 查看 APK 内所有文件的原始大小和下载大小
  • 分析 DEX 文件中的类、方法、字段数量
  • 查看资源文件的压缩情况
  • 对比两个 APK 版本的差异

APK 内部到底长什么样?

一个 APK 其实是个 ZIP 压缩包。解压后你会看到这些核心部件:

文件/目录 说明 体积占比(典型)
classes.dex 编译后的 Java/Kotlin 字节码 30% - 50%
resources.arsc 编译后的资源索引表 5% - 15%
res/ 图片、布局、字符串等资源 20% - 40%
lib/ Native 库(.so 文件) 10% - 30%
META-INF/ 签名信息、清单文件 1% - 3%
AndroidManifest.xml 应用配置清单 < 1%

嗯,这里要注意:下载大小原始大小是两个概念。Google Play 统计的是下载大小,也就是 ZIP 压缩后的体积。APK Analyzer 会同时显示这两个值,方便你判断哪些文件压缩率低、值得优化。

如何用 APK Analyzer 揪出体积「元凶」?

打开 APK Analyzer 后,我一般按这个顺序排查:

  1. 看总览:右上角会显示「Raw Size」和「Download Size」,先心里有个数
  2. 点开 res/ 目录:按大小排序,看看哪些图片或资源文件最大
  3. 检查 lib/ 目录:有没有不必要的 .so 文件?比如只用了 armeabi-v7a,却打包了 arm64-v8a 和 x86
  4. 分析 DEX:点击 classes.dex,查看「Referenced Methods」和「Referenced Fields」数量

我的小技巧:在 APK Analyzer 里选中一个文件,按 Ctrl+C 可以复制它的路径。配合「Compare with…」功能,可以对比两个版本的 APK,快速看出哪里变大了。

减少 APK 体积的实战方法

我曾经接手过一个项目,APK 体积 72MB,用户反馈安装包太大。我用 APK Analyzer 一查,发现 res/ 目录占了 38MB,其中大量 PNG 图片没有压缩。下面是我总结的几条「瘦身」经验:

1. 图片资源优化

  • 使用 WebP 格式:相比 PNG,WebP 能减少 25% - 35% 的体积。Android Studio 自带转换工具,右键图片 → Convert to WebP
  • 开启资源混淆:在 build.gradle 中设置 shrinkResources true,配合 minifyEnabled true,可以移除未使用的资源
  • 使用矢量图:对于图标、简单图形,用 VectorDrawable 替代 PNG。一个 SVG 转成的 VectorDrawable 可能只有 1KB,而 PNG 动辄 10KB+

2. DEX 文件瘦身

  • 开启代码混淆:ProGuard 或 R8 可以缩短类名、方法名,移除无用代码。我见过一个项目开启 R8 后 DEX 体积减少了 40%
  • 避免方法数超限:如果方法数超过 65536,会生成多个 DEX 文件。检查依赖库,移除不必要的库

3. Native 库精简

  • 按需打包 ABI:在 build.gradle 中配置 ndk { abiFilters 'armeabi-v7a', 'arm64-v8a' },只保留你需要的架构
  • 使用 Android App Bundle:Google Play 会根据用户设备架构只分发对应的 .so 文件,能省下不少体积

4. 资源文件清理

  • 删除未使用的资源:Android Studio 的 Refactor → Remove Unused Resources 可以帮你扫描
  • 复用资源:比如不同分辨率的图片,如果差异不大,可以只保留一套,用 scaleType 适配

避坑指南:我曾经在开启 shrinkResources 后,发现某个动态引用的图片被误删了。原因是资源通过 getIdentifier() 方式引用,混淆工具无法识别。解决方案是在 res/raw/keep.xml 中手动声明保留。

APK 分析知识体系

下面这张图帮你理清 APK 分析的完整流程:

APK 分析知识体系 APK 组成 分析工具 优化手段 验证 classes.dex resources.arsc res/ 资源 lib/ Native库 APK Analyzer 对比功能 DEX 分析 资源预览 WebP 转换 代码混淆 ABI 过滤 资源混淆 重新分析 APK 对比优化前后 确认功能正常 目标:在保证功能完整的前提下,将 APK 体积降到最低

实战:一个完整的分析流程

假设你刚打完一个 Release APK,想看看能不能再瘦一点。我会这么做:

  1. 打开 APK Analyzer,拖入 APK 文件
  2. 查看总大小:比如 Raw Size 是 28MB,Download Size 是 22MB
  3. 展开 res/ 目录:发现 drawable-xxhdpi 里有一张 2.3MB 的启动图,格式是 PNG
  4. 右键 → Convert to WebP:选择「Lossy」质量 90%,体积降到 680KB
  5. 检查 lib/ 目录:发现同时有 armeabi-v7a 和 arm64-v8a 的 .so 文件,但项目只用了前者。在 build.gradle 中加上 abiFilters 'armeabi-v7a'
  6. 开启 R8 混淆:在 release 构建类型中设置 minifyEnabled trueproguardFiles
  7. 重新打包,再次用 APK Analyzer 分析:Raw Size 降到 18MB,Download Size 降到 14MB

一个小提醒:每次优化后,记得用 APK Analyzer 的「Compare with…」功能对比前后差异。我曾经优化完发现某个资源文件反而变大了,一查是 WebP 转换时选了无损模式,图片尺寸还变大了。换成有损 90% 质量后,肉眼几乎看不出区别,体积却小了一半。

APK 分析这件事,说白了就是「知己知彼」。你只有知道 APK 里装了些什么,才能精准地砍掉冗余。APK Analyzer 就是你的手术刀,用好了,安装包瘦个 30% 到 50% 完全不是问题。


公众号:蓝海资料掘金营,微信deep3321