项目需求一改再改,UI一调 再调,结果就是项目中一堆已经用不到但却没有清理的垃圾资源,不说工程大小问题,对新进入项目的人或看其他模块的代码的人来说,这些没清理的资源可能也可 能会带来困扰,所以最好还是清理掉这些垃圾,对于一个稍微大一点的工程来说,手工清理明显是不现实的,这就需要一个方法做这些事情。
清理资源文件
要清理没用的资源,首要的工作当然是找到他们,我们知道Anroid SDK中有一个工具叫lint,可以帮助我们查看工程中存在的问题,其中有一项功能就是查找没用到的资源,这样这一步就简单了,直接对需要清理的工程执行以下命令:
lint --check "UnusedResources" [project_path] > result.txt
执行完以上命令后工程中关于UnusedResources的问题就都保存到result.txt了,先来看一下result.txt的内容
res/values/arrays.xml:202: Warning: The resource R.array.msg_my_friend_category_items appears to be unused [UnusedResources]
^M
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
res/layout/back_up_level_list.xml: Warning: The resource R.layout.back_up_level_list appears to be unused [UnusedResources]
res/layout/backup_list.xml: Warning: The resource R.layout.backup_list appears to be unused [UnusedResources]
res/layout/backup_listview_item.xml: Warning: The resource R.layout.backup_listview_item appears to be unused [UnusedResources]
可以看到列出了没用到的layout及没用到的values值等信息。有了这些信息,接下来需要做的就是分析这些信息了,手工分析不太现实,因为这个文件可能会非常大,比如我执行上述命令后文件就有2212行,这种事情,当然是交给计算机解决了。
仔细看生成的文本中的内容会发现结果是按行输出的,每个问题是单独的一行,而且每一行中的内容也很有规律
file_path[:line]: Warning: info [UnusedResources}
所以还是可以很方便地得到哪个文件甚至哪行有问题的,我处理的时候只清理了没用的文件,像上面的res/values/arrays.xml:202就没有管,下面看下怎么清除没用到的资源文件。
String projectPath = "***";
BufferedReader reader = new BufferedReader(new FileReader("/home/angeldevil/result.txt"));
String line;
int count = 0;
while((line = reader.readLine()) != null) {
if (line.contains("UnusedResources") && !line.contains("res/value") && !line.contains("appcompat")) {
count++;
int end = line.indexOf(":");
if (end != -1){
String file = line.substring(0, end);
String f = projectPath +file;
System.out.println(f);
new File(f).delete();
}
}
}
程序非常简单,就几行代码,就是读取result.txt文件的每一行,根据自己需要的条件过滤掉不需要处理的行(比如我只想清 理anim、drawable及layout,所以过滤掉res/value目录下的信息,并且忽略appcompat相关的信息),每一行":"前的字 符串就是文件名,找到了文件名就好处理了,直接删除,或者打印出来,或者写到一个文件里以再次确认是否确认要删除,当把结果写到一个文件后我们就可以查看 这个文件是否有现在没用到但仍不想删除的文件,如果有,处理方法也很简单,去掉这一行或简单地做个标记,如前面打#,然后再读取这个文件把没做标记的行对 应的文件删除就行了。
看起来很简单,但是有几点需要注意:
- 有些layout文件,可能你之前用了他们,并在相应的Java文件中用了这个layout布局中的id,如对某些ID的控件设置了 onClickListener,并在onClick的switch...case中引用了这些ID,但最后又不用这个Layout了,这时这个 layout就是UnusedResource,但是以前引用它的Java代码中对这个layout中的某些ID的引用还没清除,此时删掉这个 Layout就会报错,你可以选择清理报错的Java代码,因为它们其实时Dead Code。或者每次清理一部分资源文件,如先清理layout,再清理drawable,对于每一项也可以根据文件名的规则每次再清理一小部分,如只清理 res/layout中以item_of开头的文件。
- lint的分析貌似是不完全准确的,或者说不够智能,比如有一个drawable只被一个layout引用,而这个layout又是Unused的,lint可能不会发现这个drawable是Unused,这就需要我们多次重复执行前面的步骤,直到count为0。
- lint只能分析资源文件,即res目录下的文件,如果要分析Java文件还需要其他方法,而且,有可能某个资源文件被某Java文件引用,而这个Java文件又是Unused,这样这个资源文件就会逃过lint的检查,所以我们最好先清理了Java文件再清理资源文件。
清理Java文件
首先还是要找到未用到的文件,还是利用工具,我用的是UCDetector,即Unused Code Detector,使用方法就不说了,直接Google一下。
安装Eclipse的UCDetector插件,对工程执行检查,这个需要的时间可能会很长,我当时检查了两个小时。。同lint一样,结果会输出到一个文本文件中,同样是每个问题一行,所以只要行分析就行了,比如这样:
com..SampleAdapter.(SampleAdapter.java:18) Class "SampleAdapter" has 0 references SampleAdapter org.ucdetector.analyzeMarkerReference
com..SampleAdapter.(SampleAdapter.java:56) Change visibility of Member class "SampleAdapter.ViewHolder" to private - May cause compile errors! SampleAdapter.ViewHolder org.ucdetector.analyzeMarkerVisibilityPrivate
可以看到,检测结果中包含很多信息,如某个类没被用到,某个方法的可见性太大等,同样的,现在只处理没用到的类文件,其他不管了。
String reportPath = "**/ucdetector_reports/UCDetectorReport_001.txt";
BufferedReader reader = new BufferedReader(new FileReader(reportPath));
String line;
int count = 0;
while((line = reader.readLine()) != null) {
if (line.contains("Class") && line.contains("has 0 references") && !line.contains("Method")[ && other conditions]) {
count++;
int end = line.indexOf(".<init>");
if (end != -1){
String className = line.substring(0, end);
System.out.println(className);
}
}
}
通过以上代码基本上就能找到没用到的类了,还是建议不直接删除而是把结果输出出来,因为结果输出来以后你会发现很多文件你是不想删除的,如:
com.nostra13.universalimageloader.core.assist.DiscCacheUtil.(DiscCacheUtil.java:31) Class "DiscCacheUtil" has 0 references DiscCacheUtil org.ucdetector.analyzeMarkerReference Sergey Tarasevich (nostra13[at]gmail[dot]com)
某些类库中的文件也可能会被检测出来,对于这种直接在if条件中过滤掉就好了,也可能自己的一些文件暂时没用到但不想删除,从结果中过滤就好了。
总结
清理资源就两个步骤:
- 找到未用到的资源
- 按需清理这些资源
通过UCDetector和lint基本上就可以检测到项目中UnusedResource相 关的问题了,一般像方法可见性,某个方法没用到这种问题,不处理也罢,改到相应的文件时手工处理算了,主要处理的就是某些文件或类没被用到,有检测报告, 分析下报告就行了。这种报告一般是每行报告一个问题并且每行的文字是有规律的(工具生成的肯定有规律),按规律过滤出我们需要的信息就行了
相关推荐
本文将详细介绍如何进行Android APP瘦身,即清除工程中未使用的资源,以提高应用性能和减少开发者在阅读代码时的困扰。 首先,Android SDK提供了一个名为`lint`的工具,它能帮助开发者检查项目中的潜在问题,包括...
----------------------------------- Android 编程基础 1 封面----------------------------------- Android 编程基础 2 开放手机联盟 --Open --Open --Open --Open Handset Handset Handset Handset Alliance ...
在这个名为"Android游戏源码注释详细的五子消除项目.zip"的压缩包中,我们可以预见到一个关于Android平台上的五子棋消除游戏的完整开发项目。这个项目对于想要学习Android游戏开发,特别是对五子棋游戏逻辑和界面...
Android的MediaPlayer或SoundPool类可以用来加载和播放音频资源。 7. **分数系统**:游戏中通常会有分数计算,当消除彩球时根据连击数量和消除的彩球类型计算得分。这部分涉及数据处理和可能的动态难度调整。 8. *...
在创建“连连看”项目时,首先要在Android Studio中新建一个Android工程,选择适当的项目模板,配置项目属性,包括目标设备版本、最小SDK版本以及应用的包名。 2. **编程语言** Android应用主要使用Java或Kotlin...
在Android开发中,为了保护应用的安全性和优化APK的大小,开发者通常会使用混淆技术。Android Studio通过集成Proguard工具来实现这一目标。Proguard是一个强大的工具,它能执行四个关键操作:Shrinking(压缩)、...
在2D游戏开发中,我们通常会用到精灵(Sprites)和精灵表(Sprite Sheets)来管理游戏图形资源。泡泡龙游戏中的每个元素,如泡泡、背景、玩家控制的角色等,都是通过精灵来实现的。Unity3D的2D系统支持创建和管理...
以上就是连连看小游戏在Android开发中涉及的主要技术点,对于想要学习Android游戏开发的人来说,这是一个很好的实践项目,可以锻炼到基础的编程能力、UI设计、算法思维和软件工程实践。如果你对此感兴趣,可以从提供...
它们包含了各种预编译的类和资源,供开发者在项目中引用以实现特定功能。然而,随着时间的推移,项目可能会积累大量的jar包,其中可能包含许多未被使用的类和方法。这不仅会占用硬盘空间,还会增加构建时间和运行时...
5. 图片排列与管理:在开发过程中,这些图片会被组织到Android工程的drawable目录下,根据分辨率的不同,可能会有drawable-mdpi、drawable-hdpi、drawable-xhdpi等不同的子目录,以适应不同设备的屏幕需求。...
开发者可以通过导入这个工程文件,在Android Studio中直接查看和运行代码,进一步学习和调试。 总的来说,“多库俄罗斯方块Andriod版本”项目不仅展示了如何在Andriod平台上构建一个2D游戏,还提供了学习Andriod...
《三连镇》是一款在ANDROID平台上广受欢迎的小游戏,它以独特的消除玩法和可爱的画面吸引了不少玩家。将这样的游戏移植到PC平台,可以为更多用户带来乐趣,同时也为开发者提供了跨平台开发的实践经验。本教程将详细...
在Android和iOS平台上,Flutter的应用启动过程可能会出现性能瓶颈,导致界面颤动,这通常是由于资源加载、渲染或是初始化过程中的延迟引起的。 【描述】"恩多福"可能是对Flutter的音译,这里可能是作者对这个项目的...
4. **协程(Coroutines)**:在"无记录者"项目中,可能会用到协程来处理异步操作,如录音或文件读写。协程是一种轻量级线程,可以在不消耗大量资源的情况下实现并发。 5. **Anko库**:Kotlin社区开发的Anko库可以...
这段代码可能是贝岭在研发Linphone iOS版本时用到的工具,用于模拟、分析或优化通信过程中的某些特定算法。 【标签】"系统开源" 表明整个Linphone项目是开放源代码的,这意味着任何开发者都可以查看、使用、修改和...