Android性能优化总结

第一章Android应用性能优化(概述)
应用程序的性能问题是最明显、最容易体现的一类,表现形式也五花八门,举几个例子:

应用程序第一次启动速度慢,或者进入某一界面速度慢;
启动某一有动画效果的界面,动画执行过程不流畅,或者动画执行前卡顿时间长;
ListView列表滑动过程中卡顿,不流畅;
应用程序自定义的某特定界面执行速度慢,例如Launcher应用桌面左右滑动效果不平滑;
响应某一用户事件时长时间无响应(ANR);
操作数据库时,执行大量数据的增删改查操作,执行速度慢;
应用长时间运行后,随机出现卡顿现象;
除了表现形式复杂,原因也很复杂。以上的问题的原因可能不只一个,并且很多情况下并不是应用本身的问题,也有可能是系统其他层次有问题,只不过体现在应用层。所以说应用层总是首当其冲,开发人员在处理性能问题时,需要做的第一件事情就是判断是否是应用自身引起的性能问题,然后再对症下药;但有些时候应用本身逻辑正常,明显是系统的硬件配置不足引起,此时就要根据产品或项目需求,采取一些更加激进的方式优化性能,以弥补硬件配置的不足。

一、基本思想
应用层的性能优化通常可以从以下几个方面考虑:

二、编程技巧
(一)Performance Tips (For Java)

需要说明的是,文章列出的优化技巧主要是一些微小的性能提升,决定程序整体性能的仍然取决于程序的业务逻辑设计、代码的数据结构和算法。研发人员需要将这些优化技巧应用到平时的编码过程中,积少成多,也会对性能有很大的影响。

写出高效的代码需要遵循两条原则:

不执行不必要的操作;
不分配不必要的内存;
两条原则分别针对CPU和内存,完成必要操作的前提下尽可能的节省CPU和内存资源,自然执行效率要高。单纯这样说听起来很虚,毕竟没有一个统一的标准判断什么是必要和不必要的,需要结合具体情况具体分析了。

如果一个方法不需要操作运行时的动态变量和方法,那么可以将方法设置为static的。
常量字段要声明为”static final”,因为这样常量会被存放在dex文件的静态字段初始化器中被直接访问,否则在运行时需要通过编译时自动生成的一些函数来初始化。此规则只对基本类型和String类型有效。
不要将视图控件声明为static,因为View对象会引用Activity对象,当Activity退出时其对象本身无法被销毁,会造成内存溢出。
3. 避免内部的Getters/Setters

一种解决这个问题的方法就是将外部类的私有成员改为包级别的,这样内部类就可以直接访问,当然前提是设计上可接受。

Java标准库和Android Framework中包含了大量高效且健壮的库函数,很多函数还采用了native实现,通常情况下比我们用Java实现同样功能的代码的效率要高很多。所以善于使用系统库函数可以节省开发时间,并且也不容易出错。

(二)布局性能优化

布局的性能优化之所以重要,因为以下两个方面:

· 布局文件是一个xml文件,inflate布局文件其实就是解析xml,根据标签信息创建相应的布局对象并做关联。xml中的标签和属性设置越多,节点树的深度越深,在解析时要执行的判断逻辑、函数的嵌套和递归就越多,所以时间消耗越多;

· inflate操作只是布局影响的第一个环节,一个界面要显示出来,在requestLayout后还要执行一系列的measure、layout、draw的操作,每一步的执行时间都会受到布局本身的影响。而界面的最终显示是所有这些操作完成后才实现的,所以如果布局质量差,会增加每一步操作的时间成本,最终显示时间就会比较长。

也就是说,在达到同样布局效果的前提下,xml文件中树的深度尽量的潜。要做到这一点需要合理的使用布局控件:

典型的情况是你可以使用RelativeLayout来代替LinearLayout实现相同的布局效果;
还有一种是如果布局树的A节点只有一个子节点B,而B只有一个子节点C,那么B通常是可以去掉的;
合理的使用标签,如果布局X可以被include到Y中,那么需要考虑X的根节点是否可以设置为,这样在解析时会将的子节点添加到Y中,而本身不会添加。
2. 使用Lint分析布局

· HV的树视图展现了视图控件的相互关系,可以用来检查是否有第1点中提到的情况。

· 树视图中可以显示每个节点measure、layout、draw的时间,并且每一项用一个圆点表示其耗时是否正常,每个圆点分别用绿色、黄色、红色表示耗时正常、警告、危险,这样就可以很方便的找到有性能瓶颈了。如果树视图中没有显示这些时间,你可以点击”Obtain layout times for tree rooted at selected node”按钮刷新界面显示。

三、工具使用
遵循好的编码习惯可以让程序执行更有效率,但是实际运行时仍然会遇到各种各样的性能问题。幸好有很多强大的工具能帮助我们分析性能瓶颈,找到问题所在。以下介绍的工具想必大家已经很熟悉了,网上有很多相关文章写的都很不错,在此不再赘述,仅对这些工具在使用时的一些关键点做一些说明。关于这些工具的详细使用方法请见网上的一

(一)Traceview

Traceview就是用来分析函数调用过程的工具,利用它可以方便的分析性能问题。它的使用方式需要以下几步:

使用Android的Debug API,或者DDMS监控程序运行过程;
复现有性能问题的场景,用第1步的方法获取程序过程中的函数调用日志文件,即trace文件;
使用Traceview导入trace文件即可;
Traceview的界面很直观,但是在分析过程中需要特别注意以下几点:

· Incl – 指函数本身和内部嵌套的其他函数的执行时间;

· Excl – 指函数本身,不包含内部嵌套的其他函数的执行时间;

· Cpu Time – 指函数执行时所占用的CPU时间片的总和,不包含等待调度的时间;

· Real Time – 指函数执行过程的真实时间,包含等待调度的时间;

· Cpu Time/Call – 指函数平均每次调用的CPU时间;

· Real Time/Call – 指函数平均每次调用的真实时间;

· Calls+Recur Calls/Total – 指函数调用的总次数+递归调用次数百分比;

· % – 带有%的列是指函数的执行时间占总采样时间的百分比;

1)分析有哪些函数单次执行时间长

2)分析有哪些函数调用次数过多

3)分析有哪些函数总执行时间长

4)有时我们很明确需要查看一些特定类的特定方法,可以在页面最下方的搜索条中搜索,不过好像只支持全小写输入。

(二)dmtracedump

dmtracedump是SDK的tools目录下的可执行文件,你可以查看它的帮助信息,并执行类似如下的命令:

dmtracedump -h -g tracemap.png path-to-your-trace-file > path-to-a-html-file.html

然后就可以得到两样东西,一个是各函数调用的树状图,可以一目了然的查看函数关系;另一个是可操作的html的文件,用浏览器打开就可以方便的查找你关心的类或函数。

(三)systrace

四、关于性能优化的思考
性能优化是一个很大的话题,除了讨论如何优化外,还有一个更重要的就是是否需要优化。早在几十年前,就有很多关于性能优化的讨论,然后得出一个深刻的真理:优化更容易带来伤害,而不是好处,特别是不成熟的优化。在优化过程中,你产生的软件可能既不快速,也不正确,而且还不容易被修正。

不要因为性能而牺牲合理的结构。努力编写好的程序而不是快的程序。

Original: https://blog.51cto.com/u_15657752/5334961
Author: xiyangyang8110
Title: Android性能优化总结

原创文章受到原创版权保护。转载请注明出处:https://www.johngo689.com/517750/

转载文章受原作者版权保护。转载请注明原作者出处!

(0)

大家都在看

亲爱的 Coder【最近整理,可免费获取】👉 最新必读书单  | 👏 面试题下载  | 🌎 免费的AI知识星球