探讨秋招各大顶级公司关于AsynTask的面试问题,求大神指点!!?

小弟因为在一个项目中用到AsynTask,所以面试公司基本会问到这一块,虽然之前研究过AsynTask一些问题,但一问到一些问题,还是感觉半生不熟的理…
关注者
422
被浏览
11,506

8 个回答

1、AsyncTask为什么要设计为只能够一次任务?

因为要同一个实例执行多次很麻烦,没必要。

假设允许多次 execute 同一个 AsyncTask 多次,也就是说队列中会有同一个 AsyncTask 实例出现多次。

首先 AsyncTask 需要改动很多,比如把各种状态额外保存多份,不能像现在这样简单做为 AsyncTask 的成员变量,这些先不说,从调用者角度来看:

你继承 AsyncTask 实现了自己的一个子类 MyTask,加了一些成员变量,你想多次执行同一个 MyTask,发现不对啊,我第一次执行后这些成员变量的值都变了,状态不对。还得加个 reset 函数把这些值改回初使值,再一想何必呢,我干脆重新 new 一个 MyTask 不是更简单有效吗。

另外,虽然用默认的 Executor 是不会同时运行的,但你 execute 时如果用了自己定义 Executor,是有可能会多线程同时访问的。这时你也会想还要搞线程同步太麻烦了还是我还是 new 两个 MyTask 别想着同一个 MyTask 运行两次好了。

所以,你看,就算人家允许你同一个 AsyncTask execute 多次,你既然也不会用这功能的话,我就干脆不许你 execute 两次好了。

2、AsynTask造成的内存泄露的问题怎么解决,比如任务还在请求中,但这个Activity已经被销毁了,这个task就仍然持有act的引用,造成内存泄露?

@双羽四足

所说,最主要的是在 Activity 销毁时就应该把所有属于这个 Activity 的 Task cancel 掉。不让 Task 的活得久于他的主子 Activity。

你的 Task 应该在 onCancelled 函数中做相应的处理。比如说如果 Task 是用 来联网的,就应该在 onCancelled 中 disconnect。然后在 onCancelled 中将指向 Activity 的引用设为 null;

把指向 activity 的引用改成弱引用更多的是一份保险,保证如果你在没有正确 cancel Task 时,不会让本应去死的 Activity 还因为 Task 的强引用还在内存中晃悠。当然这个保险是很有必要的。

另外管理 Task 的生命周期也可以使用 AsyncTaskLoader 来代替 AsyncTask,由 LoaderManager 来帮你管理生命周期。

3、task执行完返回结果在已经被销毁的act显示,会如何?

如果 onPost 执行了在这个 activity 直接创建的 dialog 的 dialog.dismiss 可能会报 view not attached to window manager 异常。

同样也是生命周期的问题,用 DialogFragment 管理好 dialog 的生命周期的话不会出这个错。

4、Act销毁但Task如果没有销毁掉,当Act重启时这个task该如何解决?

最多就是 Task 指向 Activity 的引用改成弱引用了。 Task 如果是 Activity 一个成员的话已经泄漏无法访问了。

你告诉面试官老子早不用什么狗屁task了,有个东西叫RxJava,可能有两种,一种,面试官没听过,你转身就走。另一种当然是面试通过啦~~

补充下,其实如果你有过java基础,就应该知道异步线程这个东西应该自然死亡,而不是被弄死,aynctask也不过是简单的消息处理机制的封装罢了,看看源码就知道了~手打好累~就酱