【问题标题】:Memory leaks when using static context items in android在android中使用静态上下文项时内存泄漏
【发布时间】:2021-12-31 15:24:33
【问题描述】:

所以我有一个带有静态 UI 元素的类,如下所示:

class MyClass {
    companion object {
        lateinit var item:ChannelItem
    }
}
// Item from groupie
class ChannelItem(var channel:Channel): Item<ViewHolder>() {
    // bind
    // getLayout
}

这似乎导致了内存泄漏,有没有快速修复它而又不太多更改代码的方法?

我正在考虑用

替换该项目
var map = mutableMapOf<String, ChannelItem?>()

这会修复内存泄漏吗?如果是,为什么?

非常感谢

【问题讨论】:

    标签: android kotlin memory-leaks android-context groupie


    【解决方案1】:

    静态 UI 元素在 Android 中毫无意义 首先,UI 对象绑定到特定的 Activity。它们不能在其他活动中使用,也不能在其活动之外显示。因此,将它们设为静态不会带来价值

    其次,这将始终是内存泄漏。每个视图都有对其 Activity 的引用。将 Activity 放在静态变量中意味着它不能被垃圾收集,因为它有一个有效的引用。这基本上会导致该 Activity 中的每个变量泄漏。包括 UI 元素,这些元素往往会占用大量内存(每个图像每个像素占用 4 个字节)。

    您需要重新考虑要使用此代码执行的操作。我其实说不出来。如果您将它们设为静态,以便您可以从其他活动中更改它们 - 不要那样做。使它们基于模型对象,并改为更改模型中的数据。让 UI 根据模型重新初始化。

    【讨论】:

    • 这是否也适用于存储为静态变量的片段(以便在活动之间共享它们)?像mystaticvar = null 这样的赋值也会让垃圾收集器收集它吗?
    • Fragments 也不应该作为静态数据共享,因为它们只能作为上下文显示在创建它们的 Activity 中。是的,如果存储在静态中,这会泄露它们的上下文。消除所有静态引用确实可以清除它,但是如果您要跟踪所有需要这样做的东西,那么根本不让它成为静态引用会更容易。
    • 基本上,您应该跨活动共享的唯一内容就是您的应用程序的数据。不是它的 UI 元素,也不是它的上下文。这些应该完全属于创建它的活动和上下文本身。您可以将它们存储在局部变量中,或将其作为参数传递给函数。但它不应保存在静态或任何生命周期不是 Activity 子集的对象中。
    • 所以如果我有一个片段想要在活动之间共享,我不应该将其设为静态吗?
    • 没有。您也不应该在活动之间共享它。每个活动都需要制作自己的版本。 UI 元素绑定到单个 Activity,在其他 Activity 中无法正常工作。生命周期将得到所有类型的破坏。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2014-08-27
    • 2012-08-08
    • 1970-01-01
    • 2018-04-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多