gpt4 book ai didi

java - 匿名类隐藏对局部变量的引用

转载 作者:太空狗 更新时间:2023-10-29 13:49:39 28 4
gpt4 key购买 nike

我在我的 Android 应用程序中遇到了报告的内存泄漏,经过一些调查后我几乎找到了泄漏的位置,这是简化的代码:

public class LeakTracker {
public static List<Callback> callbacks = new ArrayList<>();
public static List<WeakReference<LeakingActivity>> weakList = new ArrayList<>();

// causes leak of activity
public void startLeak(final LeakingActivity activity) {
callbacks.add(new Callback() {
// remove this line then no leak
Wrapper wrapper = new Wrapper(activity);
@Override
public void onCall() {
}
});
}

// no leak here
public void startLeak2(final LeakingActivity activity) {
weakList.add(new WeakReference<>(activity));
}

public interface Callback {
void onCall();
}

static class Wrapper {
private WeakReference<LeakingActivity> weakReference;

public Wrapper(final LeakingActivity activity) {
weakReference = new WeakReference<LeakingActivity>(activity);
}
}
}

泄漏的发生是因为我调用了一个函数“startLeak”。 Activity 变量将被泄露。但是,如果我调用“startLeak2”,泄漏就不会发生。我想知道为什么第一种情况会泄漏。包装器也使用弱引用。

LeakActivity类占用内存约30M。在 Android 设备上调用 startLeak 大约 5 次会导致 OOM。调用 startLeak2 不会。如果使用 startLeak 而不是 startLeak2,LeakCanary 工具会报告泄漏。

最佳答案

在第一个方法中,您已将 Activity 声明为最终 Activity 。这会将 Activity 的引用添加到 Callback 实例,因此泄漏的不是 Wrapper,而是 Callback 本身。

此外,请记住 Callback 是一个匿名内部类,它还将持有对外部类 LeakTracker 的引用

关于java - 匿名类隐藏对局部变量的引用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49824146/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com