3

假设我在 Activity 类中有一个内部类 AsyncTask。我必须在这个 AsyncTask 中有弱参考吗?

另外,我是否必须一直为 AsyncTask 提供弱参考?

最后,如果我将内部类 AsyncTask 声明为静态,它安全吗?

4

3 回答 3

2

是的,如果它是一个内部类,或者只是创建它自己的类,总是声明你的Asynctask静态类,尽量避免声明为非静态内部类,因为它会造成内存泄漏。阅读这里以获得更详细的解释为什么你不应该这样做

您不想使用WeakReferenceAsynctask,因为 android 2.3+ 的垃圾收集器非常激进,并且会非常快速地收集所有弱引用。弱引用通常也不是线程的好模式,它更多的是用于内存占用大的对象,如位图(但在 android 中不再如前所述)。

来自http://developer.android.com/training/displaying-bitmaps/cache-bitmap.html

从 Android 2.3(API 级别 9)开始,垃圾收集器更加积极地收集软/弱引用,这使得它们相当无效。

于 2014-08-14T08:01:57.103 回答
1

WeakReference允许进行垃圾收集Activity,因此您没有内存泄漏。

空引用意味着AsyncTask不能盲目地尝试更新不再附加的用户界面,这会引发异常(例如未附加到窗口管理器的视图)。当然,您必须检查 null 以避免 NPE。因此,使用它WeakReference来处理上述情况是一个很好的做法。是的,将你的内部类声明为是完全安全的static

WeakReference<Activity> weakActivity;

在 AsyncTask 中的某个地方,可能是构造函数或 onPreExecute:

weakActivity = new WeakReference<Activity>(activity);

onPostExecute

Activity activity = weakActivity.get();
if (activity != null) {
 // do your stuff with activity here
 }

从您开始的活动AsyncTask,传递this给构造函数。(我假设您在构造函数中编写了上面显示的赋值语句。

于 2014-08-14T07:51:08.543 回答
1

如果您WeakReference出于正确的原因使用 垃圾收集器,那么拥有一个积极的垃圾收集器就不应该打扰您。

WeakReference意味着如果没有其他人强烈指向该对象,您对该对象不感兴趣。

例如,有一个AsyncTask传递一个ImageView来加载图像的。

AsyncTask完成它的工作之后,如果没有人指向具有强引用的图像视图,这意味着ImageView用户不再可见并且它的视图已被破坏,那么为什么你可能想要引用已从屏幕上移除的视图。

所以是的,我相信你在 an 中的所有引用都AsyncTask应该是弱的,特别是与 UI“视图、活动”类似的东西相关的引用。

是的,你应该static尽可能多地声明你的内部类,这样它们就没有对其包含类的隐式引用,这将破坏我们试图通过使用来做的事情WeakReference

于 2014-08-14T08:20:45.160 回答