今日头条2020版本,今日头条更新版本

在代码合理化层面,我们从两个主要想法开始。一是通过技术手段检查并去除冗余代码,二是监控代码增长和分布。另一种有效的方法是优化编译选项。

2.1 冗余代码检查技术措施

未引用的类和方法可以通过技术手段排除。

MachO 文件具有__DATA.__objc_classrefs 和__DATA.__objc_selrefs 部分,分别表示使用的类的集合和使用的方法的集合。可以通过增量集过滤掉未使用的类和方法。

2.1.1 检查是否有不必要的类

使用otool 命令显示__DATA.__objc_classrefs 和__DATA.__objc_classlist 段。两者之间的区别可能是定义了但未使用的类。

但是,__DATA.__objc_classrefs 和__DATA.__objc_classlist 段仅提供类在二进制文件中的位置地址;它们不提供类名等可读信息。因此,在获得差异集后,您需要将它们组合起来。

命令的输出将地址转换为可读的类名。

使用脚本过滤差异集对应的类后,您必须手动选择它们。动态使用的类、从nib 或Storyboard 初始化的类以及同一文件中定义的多个类会被错误地确定为未使用的类。这个需要结合业务来解决。

最终,今日头条删除了70 个类别,IPA 大小减少了约300 KB。

2.1.2 检查无用方法

所有实现的方法都可以通过链接映射获得。可以通过grep 链接映射来获得结果。

所有使用的方法都可以通过对二进制文件进行逆向工程获得。使用otool 工具反转二进制文件的__DATA.__objc_selrefs 部分并提取可执行文件中引用的方法名称。

使用此方法获得的增量集还应排除系统API 内的协议、访问器方法等。

通过这个方法,今日头条发现了2000多种浪费的方法。结果,总共累积了大约2 MB,最长的方法大约为7 KB。考虑到移除方式的工作量和风险都比较大,目前我们只移除了一小部分。

2.1.3 精简扩展代码

由于今日头条的iOS版本必须至少支持iOS7,所以今日头条的所有库都以静态库的形式集成。通过这种集成方式,当扩展依赖于某些基础库时,这些基础库所占用的体积将完全计入扩展的体积中。

我查看了安装包中的每个文件,发现今天头条的扩展占用了大约2MB,而且扩展本身的功能非常简单,显然还有精简的空间。我们重新构建了扩展,以尽可能减少对基础库的依赖,并使用系统自己的框架完成所有功能。最终,今天的扩展大小从2MB 减少到300KB。

2.2 显示并监控各业务线的包大小占用率

在利用技术手段检查冗余代码的过程中,我们发现了这个问题。通过技术手段得到的是“未引用的类和方法”,而实际上有很多引用的类和方法。它永远不会被执行。这些方法无法通过技术手段检查,因此必须依靠精通业务的开发人员手动排除故障。

因此,我们将代码优化的思路从“检查并删除冗余代码”转变为“了解并监控各业务线的代码占用状况”。这有助于我们从全球的角度了解今日头条的代码格局,找到不“划算”的模块。

2.2.1 直观表示各业务线代码占用的安装包大小

“排查监控”第一步是查看每个业务线代码占用的安装包大小。今日头条集成的业务方向分为主端、视频、UGC、商业化、问答、火山直播等。我们的目标是获取这些业务方向的代码以及每个方向所占的安装包大小。

计算代码对包大小的贡献的基本方法是查看链接映射。互联网上有几种流行的分析链接图的工具,可以让你看到每个类和每个静态库占用的大小。然而,今日头条的业务量很大,类很多(上千个),主要功能都在主项目中而不是静态库中,而且显示每个类占用的二进制文件的大小还是不够的。从那里检查每个班级是不可能的。

我们如何将类分类到特定的业务领域?我们将项目的目录结构视为我们可以使用的线程数据。

在今日头条iOS中,经过六个月的平台搭建和不断的代码重组,项目目录结构已经比较清晰易读,并且每个组的名称都可以表明该组属于哪个业务线。看看有没有。因此,结合项目的目录结构,可以更容易地将类分类到具体的业务领域。

因此,我们开发了一个脚本(以下简称“链接图分析报告”),根据项目目录的树形结构输出每个类和组的占用大小。一些文本编辑软件(如sublime)提供的折叠/展开功能可以很容易地看到每个组的包大小占用情况,类似于在Xcode中浏览项目目录。

该脚本使用开源Ruby工具Xcodeproj读取项目目录,使用开源Python脚本linkmap.py读取链接映射,获取类和静态库大小,最后输出链接。地图分析报告。

上图:链接图分析报告显示与项目目录匹配的结果,并允许您查看每个组的包大小占用情况。

今日头条项目有数千个班级,但群组数量显然非常有限。通过手动对几组进行求和,就可以轻松获得每条业务所占用的二进制文件的大小。

这些数据也是驱动各业务线“去除冗余代码、下线和废弃业务,为包大小优化做出贡献”的基础。如果您的公司有特别大的安装包,请优先考虑包大小优化。

另外,如果你看链接图分析报告,你还会发现利润低但代码量高的商家。例如,这次我们发现“动态”业务相关代码占用的二进制文件大小实际上达到了1.4 MB。作为半离线业务,这种使用率是惊人的,需要我们加速此类代码的部署。

链接图分析报告对于企业优化业务时的指导也很重要。企业可以看到哪些子方向相关的代码在其运营中最普遍,并确定优化的优先级。

在了解各业务线占用的包大小后,我们鼓励各业务线去掉不必要的业务和代码,最终将包大小优化为1.8MB。现阶段的包大小优化,1.8MB的代码优化已经相当大了。

为了便于及时输出报告,该脚本可以集成到项目的运行脚本中,因此只需要在需要时构建,并在构建的最后一步运行该脚本即可完成分析。报告。

2.2.2 版本差异监控

然而,LTO 也有一些副作用。 LTO 会减慢编译和链接速度,因此我们建议仅在构建官方包时启用它。启用LTO 后,链接映射的可读性大大降低,并且具有更多“类”,开头为:这些数字通常很大(由LTO 全局优化引起),并且需要您手动关闭LTO 打包才能读取链接映射。

3、如何优化资源文件相比于代码合理化,优化资源文件涉及的思路更多,风险也相对较小。我们尝试进一步优化资源文件,有成功也有失败。本文中的“资源”和“图片”可以视为等同术语,因为图片是今日头条应用中可优化的主要资源。

在此包大小优化期间,今日头条应该支持iOS7至iOS11系统。今日头条遵循苹果推荐的方法,使用资产目录来管理图片。大多数照片都是png 格式。每个图像中添加一个2x 图像和一个3x 图像。下面的优化和讨论也是基于这个假设。

优化资源文件主要有以下三个思路:

(1)图像压缩

(2) 将照片存入云端

(3)检查并删除多余图像

3.1 图像压缩

当你想要优化你的资源文件时,大家第一个想到的优化方法就是压缩。我们还考虑是否可以将png 图像替换为需要更少空间的格式,例如webP。

3.1.1 PNG图像压缩

我尝试了著名的PNG压缩工具ImageOptim。该工具可以在不改变图像质量的情况下压缩图像大小。打开设置以查看并选择要使用的压缩算法。

ImageOptim将上述压缩算法应用于每个图像,比较每个压缩算法产生的图像,并选择最小的输出结果。

我使用ImageOptim 压缩了项目中的几乎所有图像。整个过程持续了几个小时。在压缩过程中,我们发现大多数图像可以压缩到原始大小的70%左右,个别图像可以达到更高的压缩率。

ImageOptim 的性能绝对令人印象深刻。然而,当我满怀期待地提交并打包我的更改时,我得到了一个稍微出乎意料的结果。项目中的图像经过ImageOptim 压缩,但ipa 大小未调整。

在查看了一些文档后,我发现Xcode 构建过程中有一个步骤称为编译资产目录。在这一步中,Xcode 将png 图像本身压缩为可以快速读取和渲染的格式。当您对项目中的图像执行ImageOptim 压缩时,Xcode 使用专有算法在资产目录编译过程中重新压缩它们。此“重新压缩”过程相当于“回滚”ImageOptim 压缩。图像可能会被放大。

这也说明,无论你如何压缩项目中的PNG图片,对于优化包大小来说都是无用的。 (不过,使用ImageOptim工具压缩jpg图像仍然有效。)

在Xcode中寻找图像相关的设置项

我们还没有对PNG格式进行过详细的研究,所以不清楚这两个压缩过程在这里是做什么的。然而,我仍然对Xcode “增长”png 图像的行为不满意,所以我开始四处寻找是否有一个设置可以让我关闭Xcode 的压缩过程。

可能的配置项:

压缩PNG 文件(COMPRESS_PNG_FILES)

优化(ASSETCATALOG_COMPILER_OPTIMIZATION)

经测试,压缩PNG文件选项仅适用于分布式资源文件,对资源目录中的资源没有影响。

将优化设置为space 对包大小没有影响,原因有两个:

(1)今日头条项目由Cocoapods管理,符合Cocoapods合并资产目录的策略。资产目录编译过程是在Cocoapods 生成的脚本内进行的,因此设置构建设置没有任何效果。

(2) 优化参数仅适用于支持iOS8及以上版本的应用。下面介绍具体的分析过程。

我想改变构建过程

由于没有合法的方法可以跳过或更改Xcode 的PNG 压缩过程,因此我想继续找出是否还有其他技巧阻止Xcode 压缩图像。

我可以干预资产目录编译过程,例如在编译期间注入脚本吗?我可以修改构建规则来自定义资产目录的处理方式吗?

在编译过程中,您会注意到资产目录编译过程中使用的工具是actool。这是Xcode 中内置的工具。 actool 位于以下路径:

不幸的是,actool不是一个脚本,而是一个编译后的二进制文件。这使得资产目录编译过程成为一个完整的黑匣子。我尝试直接删除actool工具,但这直接导致构建失败。 Xcode 的设计者显然不希望您干扰其构建过程。

通过分析今日头条项目的构建流程,我们发现今日头条项目使用Cocoapod进行库管理,并且满足一些条件,所以有效进行资产目录编译的实际流程是[CP]我在Copy Pods Resources中找到的。脚本。这也是上面设置优化参数无效的原因之一。

该脚本调用actool工具来完成最后一步。

这里可以看到actool的一些参数。改变这些参数会改变actool的压缩策略吗?不幸的是,我已经测试过删除–compress-pngs参数,增加–optimization time,增加–optimization space参数,但是这些我们发现改变并没有影响package尺寸。

为什么增加–optimization time 和–optimization space 参数对包大小没有影响?这个结果显然不符合我的预期,并且互联网上几乎没有关于ASSETCATALOG_COMPILER_OPTIMIZATION 参数的文档,因为有。不是。

通过演示实验,如果您的项目不依赖于Cocoapods,那么在脚本调用actool 时传递–optimization 空间或更改构建设置中的优化选项理论上可能是有效的。

经过多次对比今日头条项目和demo,我终于找到了问题的根源。今日头条的项目至少支持iOS 7,优化参数似乎只适用于iOS 8及以上版本。在这一轮的包大小优化中,我们还不能放弃iOS7,所以优化思路也只能到此结束。

如果您考虑更改构建规则怎么办?您可以尝试使用自定义工具来编译资产目录吗?但是,我尝试了这个,但它似乎不起作用。构建规则用于处理Xcode 无法识别的源代码类型,因此它们无法更改现有类型的编译方式。

至此,任何压缩资产目录中的PNG 图像的尝试都暂时结束。这个过程表明Xcode 对PNG 图像的压缩方式有很强的控制能力。似乎不允许第三方开发者干扰PNG 图像的压缩过程。

3.1.2 使用webP代替png

即使压缩实验失败后,我们也不打算就此止步。开发者很难干预资产目录中的图像,因此自然而然地出现了问题:“我可以放弃资产目录吗?”

放弃资产目录有两个潜在的好处:

(1)您可以考虑将PNG图像转换为其他格式,例如webP。

(1)如果您已尝试多次下载zip镜像包,并且云端有最新版本,请根据您的屏幕是3x还是2x下载对应的zip包并解压。并将其保存到沙箱中。

(2) 如果要加载图片,首先从bundle中加载,如果仍然失败,则请求该图片作为网络图片并检查。

保图片能被展示。
经过线上测试,大约95%的场景下,用户可以从沙盒中成功读取图片,剩下约5%场景下用户会将图片当作网络图片来请求。当然这个实验结论会随着图片所在的页面层级变化。
3.3 排查和清除冗余图片
资源文件云端下载虽然是一个优化安装包大小的有效思路,但多少对用户体验有一些影响。所以我们又将优化的重点放到了排查和清理冗余图片上。最后的结果证明,排查和清理冗余图片的确能带来客观有效的优化。
出去正常的排查冗余图片的流程,我们还在不断审视安装包内容时收获了意外的发现。整个排查和清除冗余图片可以分为三个方向:
(1)常规的冗余图片清理
(2)修复cocoapods带来的图片重复合并问题
(3)利用tint color精简单色图标
3.3.1 常规的冗余图片清理
随着业务迭代,有不少图片成为了永远也不会使用到的僵尸图片。这些图片往往占据着较大空间,对于冗余图片的排查和清理是包大小优化中便捷而有效的一项优化内容。 头条iOS端在三轮包大小优化中都进行了冗余图片排查,每次都能清理出的图片体现在ipa上的大小都在500KB以上,相对而言是比较可观的数值。
我们主要使用一个开源的Mac app,LSUnusedResources,来进行冗余图片的排查: https://github.com/tinymind/LSUnusedResources
这个app的原理是,对某一文件目录下所有的源代码文件进行扫描,用正则表达式匹配出所有的@\\\”xxx\\\”字符串(会根据不同类型的源代码文件使用不同的匹配规则),形成“使用到的图片的集合”,然后扫描所有的图片文件名,查看哪些图片文件名不在“使用到的图片的集合”中,然后将这些图片文件呈现在结果中。
对于头条的工程而言,由于头条在图片读取时有一些字符串拼接逻辑,所以直接使用这个开源工具有一些局限。因此我们修改了这个工具的算法部分,使之更好的适应我们的工程:
(1)考虑夜间模式_night后缀
(2)考虑ipad~ipad后缀
(3)考虑_press、_selected后缀
(4)LSUnusedResources对源代码中字符串的匹配方式较为激进,容易误判(最终体现为非冗余图片被误判为冗余图片),故改为了保守的对@\\\\\”(.+ )\\\\\”的匹配。
为了保险,用这个工具跑出冗余图片候选后,还需要依次在工程中搜索确认,才能删除。
3.3.2 修复cocoapods带来的图片重复合并问题
头条重度使用cocoapods进行库管理。随着平台化的进行,越来越多的代码被封装成了pod库,以库的形式集成进工程中。在排查安装包内资源文件的过程中,我们也发现了2个由cocoapod带来的“图片重复合入安装包”的问题。这两个问题的解决,也给安装包大小优化带来了700KB左右的优化。
png文件和asset catalog重复合入安装包
在排查安装包内容时,我们发现.app文件的最外层,有一些预期外的零散资源文件。头条的资源文件绝大部分都是用asset catalog管理,仅有个别图片以零散png的形式打入安装包中。这些图片的出现不符合预期。
经过排查,我们发现这些图片来自于一个pod库。而奇怪的是,这个pod库的确是使用asset catalog进行资源文件管理的,为什么图片还会以png的形式进入到安装包中呢?
原来,这个pod库在编写podspec的时候,用了这样的语句指定资源文件:
我们使用demo进行了测试,发现podspec中这样书写,会导致asset catalog中的图片,既作为asset catalog被合并到主工程的asset.car中,也会作为png被拷贝到安装包中。导致其中一套图片白白占用了安装包空间。
在这个例子中,使用通配符来指定pod库中的资源文件显然是不合理的,会带来不可预期的陷阱。应该以白名单的形式明确指定哪些资源文件是pod库中有效的资源文件。
cocoapods暴力合并工程内asset catalog问题
在更新另一个业务方的pod库的时候,我们还发现了一个资源文件被重复合入安装包的问题。
Pod库在podspec中是这样指定资源文件的:
在业务方自己的独立app和pod库的样例工程中,这样指定资源文件没有任何异常。但是当这个pod库接入到头条app中时,我们却发现包大小的增长超过了预期。
简单排查发现,这个Image.xcassets中的图片,既作为了一个单独的asset.car被放入了名为MyPod的bundle中,又被合并到了主工程的asset.car中,而后者是预期之外的。这导致这些图片在安装包中存在了两份。
究其原因,我们发现原来这是cocoapod的一个缺陷导致的。
在工程构建的最后一步,会执行一个Copy Pods Resources的步骤,该步骤就是执行一个Pods-NewsInHouse-resources.sh脚本,脚本内容在pod install的时候生成。 这个脚本的最末几行有这样的一个操作:
即如果工程符合某些条件,则找到工程目录下所有的xcassets,使用xcode的actool工具将这些xcassets合并为一个assets.car文件。
这里合并的是“工程目录下的所有xcassets”,也就是说,不管这个xcassets针对的是哪个target,是否被工程使用了,只要它在工程的某个子文件夹下,就会被打包进安装包中。
显然这样的暴力合并可能导致安装包莫名其妙增大、图片资源莫名其妙冲突等问题。
暴力合并需要工程符合什么样的条件?第一行的if语句列出了三个条件:
(1) WRAPPER_EXTENSION是一个环境变量,构建iOS app是一般为app,所以我们工程肯定符合
(2) xcrun —find actool查找xcode的环境中是否有actool工具,我们的工程肯定符合
(3) XCASSET_FILES是一个数组,其中有几个元素取决于有多少个pod,将xcassets写到了s.resoures中。这个条件目前头条的工程符合,而业务方独立app和样例工程不符合,所以头条的工程符合以上三个条件,该脚本会执行暴力合并步骤。
为什么cocoapods需要这样暴力合并?
因为主工程的xcasset命名不规律,文件存储位置不规律,cocoapods的开发者也找不到更好的方法来准确合并所有需要的xcassets文件,所以只能采取这种暴力的方式。
如何避免这样的暴力合并?我们思考是否能通过制定pod库接入规范来杜绝podspec中resource_bundles的指定方式,但显然这样的规范没有什么合理性,也难以得到业务方的认同。
于是我们转而思考是否能通过技术手段来填补cocoapod的缺陷?工程中的xcasset的确有无法规范命名、存储位置不规律的问题,但是它们都属于某个target,可以通过target来检索到所有应该合并的xcasset文件。
目前我们执行的解决方案是:在build phase中,在执行copy pods resources之前,执行一个脚本,替换Pods-NewsInHouse-resources.sh脚本的某一行,用更合理的合并方式取代暴力合并。
替换掉的一行是:(这一行会找出工程根目录下所有的xcassets)
替换为:(get_all_xcassets是我们写的一个ruby脚本,这一行的作用是利用xcodeproj工具找出当前target的build phase中的copy bundle resources中的所有xcassets)
也就是说,替换后我们不再暴力合并工程根目录下所有的xcassets,而只是合并当前target需要的xcassets。
回过头,我们再来分析一下指定resource_bundles和指定resources的区别。
Resource_bundles是cocoapods 0.23.0加入的一个属性,比起resources,cocoapods官方更推荐使用resource_bundles:
We strongly recommend library developers to adopt resource bundles as there can be name collisions using the resources attribute. Moreover, resources specified with this attribute are copied directly to the client target and therefore they are not optimised by Xcode.
Cocoapods的文档中提到了两点:
(1)使用resource_bundles能大大减小命名冲突的概率
(2)使用resources资源文件是直接拷贝到app中的(对于xib,xcassets等,cocoapods会用脚本进行编译),没有经过Xcode的优化(此处指的应该是零散的png)
在构建过程中,使用resources的资源文件,会在构建的最后一步Pods-NewsInHouse-resource.sh中被拷贝到app中。 使用resource_bundles的资源文件,在构建pod时,就已经被合并到bundle中了,最后在Pods-NewsInHouse-resource.sh中这些bundle被拷贝到app中。 放在resouce_bundles中的资源文件,整个构建过程更符合Xcode的构建方式,能应用Xcode的优化,跟进Xcode的版本,所以一般情况下更推荐将资源文件放到resource_bundles中。
制定pod库资源文件规范
经历了两次pod库资源文件合并带来的陷阱,我们认为有必要制定一个资源文件接入规范。
对于最低支持iOS7的pod:
我们推荐使用resource配合xcassets的方式来集成各个插件中的资源 具体的做法有:
1、Pod中的资源文件建议使用xcassets组织
(1)xcassets需要添加到podspec的resources中
(2)xcassets中的图片名,必须使用前缀;(xcassets间的命名冲突会导致读取的图片不可预期)
2、如果pod中有资源文件没有用xcassets组织
(1)这些资源文件必须放入resource_bundles中,禁止放入resource中;(resource_bundle中的资源在构建期能经过Xcode的优化,而resource中的资源不能)
对于最低支持iOS8的pod:
我们推荐使用resource_bundles配合xcassets的方式来集成各个插件中的资源文件。 具体的做法有:
1、Pod中的资源文件建议使用xcassets组织
(1)xcassets需要添加到podspec的resource_bundles中
(2)Pods中的代码,在读取图片资源时,使用imageNamed:inBundle:compatibleWithTraitCollection:读取(该方法最低支持iOS8),无法使用imageNamed:读取
2、如果pod中有资源文件没有用xcassets组织
(1)这些资源文件必须放入resource_bundles中,禁止放入resource中;(resource_bundle中的资源在构建期能经过Xcode的优化,而resource中的资源不能)
如果该pod不需要支持iOS7,则更支持使用后者方式,这样做的优点有:
(1)各个pod管理各自的资源文件,不会有命名冲突的问题
(2)能利用苹果的app slicing功能
(3)防止cocoapods暴力合并所有xcassets的引起其他潜在问题
3.3.3 利用tint color精简单色图标
在浏览了安装包内所有的图片文件后,我们产生了一个直观的感受:由于头条有日夜间模式,导致大部分图标都切出了日间和夜间两套图标,而这两套图标的形状是完全一致的,只是颜色有差异。
如果能结合tint color对单色图标做一次精简,对安装包大小和图标的管理都有正向的影响。
tint color是苹果在iOS7推出的功能,我们可以读取一个图标,然后给它赋予一个color值,在手机屏幕上它就能显示出相应的效果。tint color适用于对单色图标进行着色,相比于其他精简图标的解决方案,tint color方便、可靠、拥有原生支持。
精简图标的工作需要各业务端共同参与,可以预计将消耗较大的人力成本。为了尽量减轻业务方的负担,我们提前做了一些预备工作,包括筛选、色值抽取、色号匹配、分配到人等。这些工作均使用脚本完成。
最终我们筛选出了大约3MB、1500+张形状重复的图片,理想情况下可以精简掉其中的一半。
最后我们将候选图片以这样的文件名输出:
文件名中包含了精简所需要的全部信息,便于业务方接入。
为了将图片中的有效信息抽取出来放在文件名中,我们提前做了以下这些工作:
(1)获取ipa内的全部图片
使用工具 iOS Images Extractor可以帮助解压asset.car文件,获得ipa内全部图片。
(2)筛选“形状一致”的图片
由于我们对图像处理并没有做深入研究,所以使用了一个拍脑袋想出来的朴素方法:获取一张图片所有像素点的alpha值,alpha值完全一致的两张图片,就是“形状一样”的图片。
我们使用了ImageMagick这个工具抽取图像的每个像素点值,然后对所有alpha值做md5计算。经过目测,使用这个方式来筛选形状一致的图片还是比较有效的。
(3)获取单色图片的色值
使用ImageMagick工具,抽取图像每个像素点值,排除掉全透明的点,然后找到色值的众数,则可以认为是该单色图片的色值。
(4)获取图片的色号
拥有了色值之后,有些app可能就可以直接用色值来做后续开发了。但是头条app中不允许使用色值,必须使用UI规范中的“色号”,比如“面1”、“字1”之类的。
同时我们希望矫正那些“有一点偏差”的色值。
下图底色为标准色,而icon的颜色其实并不是标准色,有一点差,但是肉眼基本看不出来,可能是设计师在作图时手抖了。这种情况下我们就需要做“矫正”。
这个问题也可以表述为:如何将一个色值匹配到与它最接近的标准色上?
对图像没有研究,经过一番google,我知道了这个命题的关键字叫做“color distance”,于是又一番google,得知了一些公式,比如:http://colormine.org/delta-e-calculator/
最后找了一个开源的工具:http://chir.ag/projects/ntc/
这是一个js的工具,能将一个色值匹配到与它最接近的某个颜色名称上。
于是我直接将头条的标准色色值给复制到了原码里。于是这个脚本可以完成的工作是:输入随便一个色值,输出与之最接近的头条标准色色值。
最后,如何将标准色值再映射到“字x”、“面x”呢,这就需要找到一张图的日间模式和夜间模式,然后用两个标准色值去找色号名字。
(5)将图片分配到人
精简图标的工作需要各业务方来推动,所以在做准备工作时,我们需要将每个图标分配到各业务方。由于仅凭肉眼很难判断一个图标是属于哪个业务的,所以我们使用了git log作为分发依据,以谁添加谁负责为原则。
对于指定的图片名,我们首先使用mdfind命令找出它所在的路径,然后读取git log,查询到该图片的添加者,完成分类。
使用tint color着色,不仅能精简掉形状相同的夜间模式图标,可能对日间模式图标还能带来优化空间。
在使用tint color着色后,单色图片自身的颜色(RGB色值)便失去了意义。图片提供的全部信息实际就只有alpha通道的信息。在这种情况下,考虑将图片转为灰度图可以进一步缩减图片体积。
整个tint color的接入工作还在进展过程中。
总结任何优化项目都会经历一个越来越难以突破的过程。在安装包优化的过程中,我们也从单枪匹马的挖掘优化点,到形成了监控和量化体系。优化一个app可以给一个app带来转化、留存上的收益,而总结出一套优化方法并推广出去,则可以给更多的产品线带来收益。
未来我们也会持续总结优化方法,形成方法论和工具,让公司的其他产品也得到受益。甚至我们可以开发一套诊断脚本,一键得知某个app的可优化点。将优化工作推进到一个更高的层面。
最后,附上头条安装包大小优化的工作项和收益:

本文和图片来自网络,不代表火豚游戏立场,如若侵权请联系我们删除:https://www.huotun.com/game/674896.html

(0)
上一篇 2024年6月4日
下一篇 2024年6月4日

相关推荐

  • 和平精英二操作设置? 苹果和平精英操作设置?

    和平精英二操作设置? 2指操作只要设置好了就能吊打3指操作,轻松的上王牌。 玩家可以将陀螺仪给打开,这样一来,玩家们在压枪和移动射击时就很好操作,只需要转动手机,瞄准镜就会随着转动方向跟过去了,可以说是非常的方便了。 之后玩家就能专注于自己的手速,在不断的练习下让肌肉形成记忆! 苹果和平精英操作设置? 点开设置选择自定义操作设置 根据自己习惯的键位进行设置即…

    游戏快讯 1小时前
  • 和平精英键位初始键位设置号码?

    和平精英键位初始键位设置号码? 没有一个特定的初始键位设置号码,因为这个设置是根据玩家个人的操作习惯和键位偏好来进行的。但是一般来说,在游戏开始时,玩家需要点击屏幕中央的“操作”按钮,进入到“设置”页面,再选择“控制”选项,根据自己的喜好进行键位设置。在这个页面中,玩家可以设置移动、射击、切换武器、投掷物品、瞄准等操作的键位,同时还可以进行灵敏度、视角等设置…

    游戏快讯 3小时前
  • 和平精英身法必备的枪?

    和平精英身法必备的枪? 是步枪。步枪是一种全能性枪械,具有中远距离射击、连发和单发射击等多种功能,可以应对多种情况,而且精准度高,不易误伤队友。在和平精英游戏中,体现身法的关键就是要快速切换姿势,而步枪可以快速切换姿势并进行精准射击,因此是必备的。除了步枪外,一些玩家可能会选择短枪或冲锋枪等快速射击的武器来体现身法。但是这些武器的精准度和射程都相对较低,容易…

    游戏快讯 4小时前
  • 和平精英的牌子怎么获得?

    和平精英的牌子怎么获得? 方法/步骤: 1. 打开和平精英,登录好账号;进入到主页后,点击右下角的直播图标 2. 进入到直播页面之后,切换右上角的页签到“我的” 3. 在“我的”页面中,点击进入“任务中心”;通过完成任务,获取赛事币 4. 退出“任务中心”,返回到“直播”的页签;点击“助威”按钮 和平精英花瓣如何获得? 通过参加和平精英游戏内的各种活动,包括…

    游戏快讯 6小时前
  • 和平精英怎么开变声器免费?

    和平精英怎么开变声器免费? 1. 首先打开和平营地 2. 在和平营地里选择营地工具 3. 然后打开变声器 4. 启动游戏,就可以在和平精英开免费的变声器了 和平精英变声器怎么关? 1.点击设置 2.从游戏中找到游戏设置选项并点击一下。 3.点击声音设置 4.在设置界面找到“声音设置”选项进入。 5.关闭变声器 6.在变声器栏下点击关闭按钮即可。 和平精英如何…

    游戏快讯 7小时前