Apk性能优化--瘦身的那些事儿

前言:

你是否曾今被迫接手一个浩瀚又陌生的项目,面对繁杂的代码总有些力不从心且心声厌倦;你是否曾今经历码字五分钟,编译两小时;你是否曾今在下载某一款app时因为要下载很久而吐槽或放弃。而这些或多或少都和代码不规范、冗余,apk体积过大有关,因此apk瘦身在android应用的性能优化上来说也是不可绕过的一部分。接下来我们就来聊聊apk瘦身的那些事儿。

 

Apk Analyzer:

为了更好、更直观的说明apk瘦身的必要性,我特意找了一个以前无用的代码,接下来我们就给这个代码瘦个身。

Apk analyzer是android studio2.2之后自带的apk分析工具,它能够通过apk文件查看各个目录及文件的大小,可以查看apk版本信息、也可以直接比较新旧版本apk,直观的发现文件大小变化。我们可以通过点击Android studio菜单栏Build -> Analyze Apk...弹窗选择我们需要分析的apk。打开后视图如下:

Apk性能优化--瘦身的那些事儿_第1张图片 通过apk analyzer分析apk

通过上图可知,这个apk大小为172.6MB,通过Google play压缩大小为121.1MB,其中lib、assets、res是体积过大的主要文件夹。因此该apk的优化思路就是尽量去除无用的资源及jar包。接下来我们可以开始进行瘦身了,最后再通过Apk Analyzer来做一个前后比较,这样我们就可以很直观的发现是哪些地方瘦下去了。

 

Lint:

Lint是android开发者们常用的工具之一,也是Android Studio自带的代码扫描工具。它可以识别出项目中那些没有被任何代码所引用的资源文件,硬编码,重复的图标等一系列的问题。我们可以通过点击Android Studio菜单栏中的Analyze->Inspect Code...弹窗选择要扫描的具体范围然后进行扫描。我们对项目的全部内容进行扫描,结果如下图所示。

Apk性能优化--瘦身的那些事儿_第2张图片 Inspect Code扫描结果

左边是问题的列表,右边是错误的类型、文件的检测报告,也提供了一些操作建议。一般情况下我们可能只想直接清除无用资源而不关心扫描的问题。那么我们可以点击Analyze->Run Inspection by name弹窗直接搜索"unuser resources"无用资源来进行扫描。扫描结果如下,点击Remove All Unused Resources来清除无用资源。

Apk性能优化--瘦身的那些事儿_第3张图片

我们也可以在Gradle中配置lintOptions来更好的使用Lint。

    lintOptions {   //关于Lint的Gradle配置
        // 关闭对您指定的问题ID的检查。
        disable 'TypographyFractions','TypographyQuotes'
        // 打开对您指定的问题ID的检查。
        enable 'RtlHardcoded','RtlCompat', 'RtlEnabled'
        // 要仅对问题ID的子集启用检查并忽略所有其他问题,请改为使用“ check”属性列出问题ID。
        // 此属性将覆盖您使用上述属性启用或禁用的所有问题ID。
        check 'NewApi', 'InlinedApi'
        // 如果设置为true,则关闭lint的分析进度报告。
        quiet true
        // 如果设置为true(默认值),则在发现错误时停止构建。
        abortOnError false
        // 如果为true,则仅报告错误
        ignoreWarnings true
    }

 

减小libs体积:

在NDK开发过程中往往会加入一些.so动态库,它们会被添加到“x86”、“x86_64”,“armeabi”、“armeabi-v7a”和“arm64-v8a”下,在实际的引用中应用程序会根据手机的cpu来选择对应文件夹下面的so库去执行。因此优化思路就是去除那些不会被cpu所调用的动态库文件。“x86”和“x86_64”通常在android模拟器上被使用,它们的区别在于是32位还是64位系统,“armeabi”针对的是普通的或旧的arm cpu,而"armeabi-v7a"则针对有浮点预算和高级扩展功能的arm v7 cpu。“arm64-v8a”是针对64位arm。了解了这些之后,我们可以根据应用的受众群体来合理的配置动态库。我们这里可以只支持"armeabi-v7a"即可,删除其他所有的文件夹及文件夹下的so库(记得备份哟),并在Gradle下配置abiFilters,如下所示:

    defaultConfig {
        ......      
        ndk {     //设置支持的SO库架构(开发者可以根据需要,选择一个或多个平台的so)
            abiFilters "armeabi-v7a"
        }
    }

 

图片和动画的优化处理:

瘦身无非就两点,一个是“删除”、一个是“压缩”。通过上面的方式该删除的也都删的差不多了,接下来就是压缩的事儿了。首先我们可以将大部分图片格式替换成webp格式。webp是2010发布的,目的是为了减少文件大小,但达到与jpeg格式相同的图片质量。那么我们该如何将PNG、JPG等格式的图片转化为webp格式的文件呢。其实Android Studio就支持转webp格式,选择图片资源右键,找到Convert to webp...即可转为为webp格式的图片。转换后对比如下,这张图片从3.5KB缩小到了1.8KB,效果显著。

Apk性能优化--瘦身的那些事儿_第4张图片

其次是尽量不要使用帧动画,由于帧动画的特殊性会占用大量的空间,因此在项目中能避免就避免使用帧动画,有时候交给UI解决会比我们自己处理好很多。最后有些图片资源也可以交由服务器存储,在必要时再下载使用。

 

其他:

有时候我们会引用一些第三方的jar包,但是又只用了里面一小部分功能,那么这时候我们可以考虑下载并引用完整代码来替换jar包,同时删除我们不需要的代码,只保留需要的功能代码即可,当然删减别人的代码这并不容易,因此我们可以在所有的优化瘦身完成之后再考虑优化这些第三方jar包。

如果项目中只需要支持少量的语言,我们也可以在Gradle中配置:

    defaultConfig {
        ......
        resConfigs "zh"
    }

另外我们还可以设置shrinkResources为true来在编译过程中删除所有未被使用到的资源文件,其优点是不需要我们删除物理资源。要使得shrinkResources起作用,必须保证minifyEnabled 为true,因此其配置如下:

    buildTypes {
        release {
            minifyEnabled true
            shrinkResources true    //删除所有未被使用到的资源文件
        }
    }

 

总结:

最后我们再通过apk analyzer的比较功能来比较一下瘦身前后的apk的体积变化。

Apk性能优化--瘦身的那些事儿_第5张图片 apk瘦身前后对比图

从上图我们可以看到经过一系列瘦身之后的apk总大小减少了65.9MB,减小了38.2%,效果还是很显著的。当然这里lib中的一些第三方jar包,assets中的资源还可以进一步优化压缩,我这里就没有一一演示了。

 

参考资料:

Android性能优化之APK瘦身详解(瘦身73%)

Android 工程师进阶 34 讲

Android Develop -- WebP

你可能感兴趣的:(Android应用的性能优化)