2009-10-01 113 views
5

什么是最容易犯的错误,可能会导致Android性能下降?Android上常见的性能陷阱?

文档中提到“某些浮点运算”可以是“毫秒级” - 是否有人测试过它?

为了便于讨论,我们假设它在G1 /类似设备上运行。

回答

0

他们希望你避免使用浮点数是因为它是很少的原因在手机CPU上实现(可能是手臂),并且必须用慢速的软件来实现。固定点虽然在硬件方面被惯用。

某些电话确实在硬件中实现了浮点运算,但由于您不需要将应用程序部署到哪个电话上,因此不会冒险。

很多人也说避免使用对象,回到真正慢手机和java时代,我习惯用静态函数编写java程序。我现在不会推荐。

0

不要担心性能,直到您知道代码有重大问题。小小的调整(ints而不是浮点数,使用迭代器而不是显式数组枚举)往往是非常小的,当你的应用程序关闭时你最好看着它们。让5%的代码更慢,而不是制作整个应用程序。

+4

虽然我同意不优化早期等,这不是问题在这里。例如,如果所有浮点操作都需要1ms,并且所有的int操作都是1ns,那么从头开始设计固定点的所有数据结构就是常识。 – Viktor 2009-10-01 18:41:47

+0

如果你有一个50ms的预算来完成这项工作,如果需要1ms或1ns没有关系。获取代码工作,然后担心细节。固定点和浮点之间的转换最多只需要一天或两天的时间。 让你的应用程序运行高效的算法,然后如果你需要做这些优化。 在我看过的几乎每个应用程序中,大型性能优势永远都不是微型优化。他们正在确保你不做愚蠢的事情(绘制对象2x,在不需要时进行排序,...)。 有些情况下,微型优化是正确的。当它发生时,你会知道它 – hacken 2009-10-15 22:01:48

0

根据Android的人,你应该避免使用接口名称的集合。例如,对于标准的Java标准的最佳做法是说

List<String> strings = new ArrayList<String>(); 

而在Android的,他们说这是更好地与它的运行时类型声明它

ArrayList<String> strings = new ArrayList<String>(); 
+8

注意 - 尽管在文档中 - 这实际上并不正确。我已经在froyo的文档中更正了这一点。 (特别是,文档的froyo版本不会包含任何基准没有证实的索赔。) – 2010-02-24 07:29:24

2

WRT浮点:

在G1上,增加两个浮点大约需要400ns。增加两个整数大约需要250ns。

上运行eclair(前JIT),操作需要约120ns。 (整数稍微快一点,但你必须注意微基准。)int和long,float和double之间有一个很小的百分比差异,但基本上如果你能买得起它,你可能买得起另一个。

其他目前的设备将介于这两个极端之间。 (其他操作也会有所不同,乘法比加法/减法更昂贵,并且除法更加昂贵,没有当前设备具有硬件整数除法。)

但是不要关注这些,直到遇到问题。很可能,您的性能问题将归结为算法或数据结构的糟糕选择,就像每个人的性能问题一样。

大部分当前(eclair)性能文档都不正确。在您关心的设备上自己设定基准。但是如果你真的在问“桌面/服务器java程序员应该注意什么?”,我会建议:不必要的分配。你没有像在桌面/服务器上那样做GC的备用内核,并且你没有像在桌面/服务器上那样拥有千兆字节的堆。如果你在做GC,那么你没有做真正的工作,而且你的堆在目前的设备上最多只有24MiB。所以你可能想要避免在内部循环中不必要的分配。

+0

*,但在您遇到问题之前不要着迷于此。 的机会是,你的性能问题会下降到可怜的 算法或数据结构的选择,就像每个人的 的性能问题总是存在。* 这是巨大的。我可以给你一个拥抱吗? – Cheezmeister 2012-06-12 23:22:23

0

我发现AppInventor仿真器对于浮点操作非常缓慢,即使在2014 i3/4Gb机器上也是如此。我写了一个分形生成器来对模拟器进行基准测试,发现要计算一个像素,到10次迭代需要超过两秒钟 - 是的,2,000毫秒。我还没有完全解决它,以找到哪些特定的操作如此缓慢,但我将尽快做到这一点。

每次迭代涉及四个乘法,两个加法和一个减法,五个变量。每次迭代后进行测试涉及两次乘法,一次加法和两次比较 - 大约30次触发。我还没有通过存储下一次迭代的结果来优化代码。显然,如果有办法强制使用固定点或只使用整数,那么这个小项目所面临的问题的严重程度就不是一个好兆头。