繁体   English   中英

Android ListView行背景导致内存不足问题

[英]Android ListView Row Background's causing OutOfMemory Issue

我有一个片段,可从Web服务中提取数据并将其显示在ListView中。 我有10个不同的选择器可用于行背景。 循环后将重复背景。

我面临的问题是设备(Galaxy Nexus!)无法处理所有这些背景的显示。 当我通过setbackgroundResource设置背景时,操作系统会不断调用GC释放内存,这使ListView的滚动非常不稳定。

因此,我尝试缓存使用的Drawables。 我看到了一个改进,但是该设备最终会由于缓存了多少Drawable而抛出OutOfMemory异常。 举一个缓存多少的例子,我需要所有10个选择器,每个选择器都包含两个可绘制对象,以及第一个和最后一个,因为它们是不同的。 这是内存中的24个可绘制对象。

现在,我在想这可能是我正在使用的图像的大小,我需要按比例缩小它们并只是按比例拉伸,但是我不确定这是否可行。

有什么建议么? 我花了几天的时间不停地工作,却没有找到可行的解决方案。

谢谢

亚当

Mimminito,

您描述的问题困扰着Android平台上的许多开发人员。 原因是当Google实施View Drawable时,他们必须做出一个有效的假设,即可能需要保留以前的Drawable。 这是因为越来越多的平台上越来越多的应用程序需要此行为。

最终,有多种方法可以缓解问题,但是没有一种方法可以解决所有问题。

  1. 替换背景时,请获取原始背景。 如果是位图,请对其进行recycle() 如果它是Drawable,则将引用设置为null并通过setCallback删除其Callback(这在更改方向或切换Activity时尤其重要)。

  2. 图形是最消耗内存的资源之一。 如果使用的是Drawable或Bitmap,则每个像素使用4个字节。 但是,如果必须调整图像大小以使其正确显示,则无论应用程序是放大还是缩小,它实际上使用了很多东西。 以高分辨率创建图形非常棒,但是对于移动设备,您希望将其缩放到实际要使用的尺寸。

  3. 如果您使用大量图形,则可以考虑仅使用那些将可见的图形。 也就是说,如果您有32个项目,但只有3个可见,则仅加载3个可见的对象,并可能加载一些直接的邻居。 可以为许多标准化控件实现延迟加载。

  4. 我建议查看.9.png文件。 这些对于优化图形非常有用。

  5. 如果您的按钮上有文字,请不要将其绘制在图形文件上。 允许Android将文本放置在图形文件上。 它的处理方式大不相同,并且内存消耗大大减少。 尽管它可能不那么美观,但会提高可靠性(这就是您在这里的原因)

  6. 在某些情况下,可能希望图形是平面位图,而不是压缩格式。 这样可以减少处理器和内存的负载,但要以文件大小为代价。 这是因为无论如何都必须在内存中对压缩格式进行解压缩才能使用,但是直到实际关闭文件后才释放内存。 (这甚至不包括用于解压缩它的运行时代码的内存,当应用程序必须调整图形大小时,这甚至会花费更多的钱)。

  7. 放入一些额外的System.gc()语句可以帮助减轻负载,但它并不可靠,因为它仅告诉系统它已准备好尽早进行垃圾收集。

  8. 最后,您可以根据设备的分辨率指定多个大小。 这是您可以通过您的应用程序传输的信息。 这就是我们必须在本地应用程序中进行多设备支持的方式。

所有这些建议可能会有所帮助,但其中包含很多信息。 希望我能给您足够的钱,以实现可以满足您需求的解决方案。

希望对您有所帮助,FuzzicalLogic

也许您将cacheColorHint设置为透明(如果您有固定的背景图片): android:cacheColorHint="#00000000" 对我而言,它还多次致电GC。

我发现设置以下属性将禁用android的列表视图缓存,并且列表滚动流畅(不再经常调用GC):

android:scrollingCache="false"
android:animationCache="false"

另外,如果您想摆脱默认选择颜色,请使用以下命令:

android:listSelector="#00000000"

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM