作者Killercat (杀人猫™)
看板java
标题Re: [翻译] 死法无法预测
时间Sat Apr 26 23:15:19 2014
※ 引述《AmosYang (Zzz...)》之铭言:
※ 引述《PsMonkey (痞子军团团长)》之铭言:
1F:推 Killercat:Fragmentation在Android上还满容易监测的就是 04/26 17:09
2F:→ Killercat:因为android的演算法相对简单 看到heap/free比例不对 04/26 19:12
3F:→ Killercat:大概要猜也猜得出来发生什麽事情了(摸下巴) 04/26 19:13
我对 Android 不熟, 能否就「看到heap/free比例不对」多说一些?
感觉是个蛮有意思的方向, 感谢 orz
-----
我好一阵子(一两年)没写Android了。Android来讲,很多动作都会造成Fragmentation
这些都可以在DDMS(Android的一种除错机制)看到Dalvik目前的记忆体使用情形
这东西有一个表格,可以列出你目前的记忆体使用情况
(顺带一提 当年Bitmap用的是完全不同的独立空间,现在我不知道还是不是)
记忆体里面有几个数值,包括Used, Free, Heap
基本上Used很浅显易懂就不解释,Free也很直观不解释
重点在於最後一个Heap
Android的Heap基本上是个只增不减的东西(4.0以後有新的做法 但是我已经没在写了)
他也是很直观的"跟系统要的记忆体"数量,VM系统大概都是有这种类似概念
问题在於,Heap什麽时候会被allocate到呢?当然是app需要空间但是free却不够的时候
一直到这里为止都还只是常识等级的概念
但是表格上有一个东西没有提到,就是破碎度。
我先假设阅读这篇的人都对破碎度有完全的了解,知道什麽是记忆体破碎
Free可能是破碎的,所以即使还有10M,但是App要从Free拿10M却不见得拿的到
因为Free可能最连续的部分只有8M。有些VM实作的JVM会在GC的时候做Memory Trim
Trim以後「也许」有机会拿到连续的10M 那就不用再去跟JVM靠背
所以大概也只有在最严苛的状况下才会变成这篇文章提到的部分
但是这是Android,这东西是Dalvik,基本上是一个沙箱化的设计
他不可能在ui thread那麽猖狂的环境下没事情给你trim一下
UI Thread = 超高负载 = 使用者体验 = 消费者 = 所有系统都要极力讨好的对象
Dalvik唯一合理的做法就是多跟heap要一点记忆体(通常就是直接要个10M了)
所以我们在DDMS里面会看到Free在一定范围内上上下下但是Heap却越来越多
更惨的情况(像是以前我手机需要写一个加解密Relay Server)下
基本上看Free就知道情况会越来越不妙,Free会开始节节高陞
但是大家都知道原因不是因为程式写的好用的记忆体少
而是因为Android的记忆体配置策略简单,而且不要说Trim 连GC都是不到最後关头不干
所以要是你写的code会造成大量空洞化,或者Fragmentation越来越严重
你就会看到很神奇的Free/Heap比例,Heap不停长,Free也跟着长
反正大家都猜的到Free里面是什麽?蜂窝吗.... XD
(这是一个当初Android开发者的双关笑话,Android 3.0叫做Honeycomb蜂窝
而这刚好也是一个记忆体空洞化(让整块记忆体看起来像蜂窝)很严重的版本)
这很好猜,超好猜,我相信做久一点的或者做深一点的Android开发者都会碰到
看数字就知道发生什麽事情了.
现在的Dalvik我不知道,但是我那时代的Android之所以开机都马不持久
一天大概要重开机个一次,我始终高度的怀疑跟这记忆体策略有关
叫我写一个系统用这种策略 我大概得天天重新开机才行了...
--
※ 发信站: 批踢踢实业坊(ptt.cc), 来自: 118.160.18.161
※ 文章网址: http://webptt.com/cn.aspx?n=bbs/java/M.1398525322.A.2B4.html
※ 编辑: Killercat (118.160.18.161), 04/26/2014 23:21:39
4F:推 AmosYang: 有趣 :D 感谢分享 orz 04/26 23:35
5F:推 gmoz:XDDD 04/28 11:35
6F:推 stiles:赞 XDD 05/06 17:32