【问题标题】:AsyncTask: Should I check for isCanceled() in onPostExecute()?AsyncTask:我应该在 onPostExecute() 中检查 isCanceled() 吗?
【发布时间】:2017-08-30 10:26:07
【问题描述】:

我正在处理相当多的遗留 AsyncTask 代码,并且我自己也必须在我们的代码库中编写一些代码。但是,仔细阅读文档中的cancel() 方法让我有些困惑。文档说:

尝试取消此任务的执行。 如果出现以下情况,此尝试将失败 任务已完成、已被取消或无法 因其他原因而被取消。 如果成功,并且此任务已 调用取消时未启动,此任务不应运行。如果 任务已经开始,然后mayInterruptIfRunning参数 确定执行此任务的线程是否应该是 试图停止任务而被打断。

调用这个方法会导致onCancelled(Object)被调用 在doInBackground(Object[]) 返回后的 UI 线程上。调用这个 方法保证永远不会调用onPostExecute(Object)。后 调用此方法,您应该检查返回的值 isCancelled() 定期从 doInBackground(Object[]) 完成 尽早完成任务。

因此,可能存在 AsyncTask 已完成并从doInBackground() 返回但在调用onPostExecute() 之前通过cancel() 取消的任务,这导致调用onPostExecute()。如果取消是从onPause()Activity 发起的,这可能会很危险。

此外,关于 SO 的这个问题支持记录在案的取消行为:onPostExecute on cancelled AsyncTask

那么,我应该从现在开始在onPostExecute() 的开头检查if(isCanceled()) 吗?

【问题讨论】:

  • "因此,可能存在 AsyncTask 已完成并从 doInBackground() 返回但在调用 onPostExecute() 之前通过 cancel() 取消任务的情况,从而导致调用 onPostExecute( ) 无论如何。如果取消是从 Activity 的 onPause() 启动的,这可能会很危险。”你遇到过这种情况吗?
  • @ProgrammingPirate :这是用于企业生产的代码。如果至少在官方文档中有记录,我该如何承担风险?
  • @ProgrammingPirate :另外,由于这是一个多线程场景,捕捉场景可能并不容易。

标签: android android-asynctask


【解决方案1】:

那么,我是否应该在开始时开始检查 if(isCanceled()) onPostExecute() 从现在开始?

肯定不是,已经检查过了。

  private void finish(Result result) {
        if (isCancelled()) {
            onCancelled(result);
        } else {
            onPostExecute(result);
        }
        mStatus = Status.FINISHED;
    }

参考:AsyncTask.java

【讨论】:

  • 其实我看到了cancel()方法,还有mCancelled.set(true);。如何阻止任何人调用此方法并设置此标志?而且,当标志被设置时,isCancelled() 在 onPostExecute() 中返回 true,这意味着此时,有人真的希望任务消失。
  • 换句话说,在finish() 方法选择onPostExecute() 之后,会调用cancel() 并设置标志。在 onPostExecute() 中,isCancelled() 肯定有可能返回 true。不是吗?
  • 如果您需要另一个线程与异步任务交互。 Asynctask 旨在仅从 UI 线程调用。来自文档:“AsyncTask 可以正确和轻松地使用 UI 线程。此类允许您执行后台操作并在 UI 线程上发布结果,而无需操作线程和/或处理程序......异步任务由在后台线程上运行并且其结果在 UI 线程上发布的计算。”
  • 还要检查“线程规则” AsyncTask 类必须加载到 UI 线程上。任务实例必须在 UI 线程上创建。必须在 UI 线程上调用 execute(Params...)。参考:developer.android.com/reference/android/os/AsyncTask.html
  • 所以如果你在ui线程中使用Asynctask,取消标志是没有问题的。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-03-30
  • 1970-01-01
  • 2013-11-21
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多