在我的Activity中,我使用了一个从AsyncTask扩展的类和一个参数,该参数是AsyncTask的一个实例 . 当我打电话 mInstanceOfAT.execute("")
一切都很好 . 但是当我按下再次调用AsyncTask的更新按钮时应用程序崩溃(如果网络作业不起作用) . 因此出现了一个例外情况
无法执行任务:任务已经执行(任务只能执行一次)
我试过为Asyctask的实例调用cancel(true),但它也不起作用 . 到目前为止唯一的解决方案是创建Asyntask的新实例 . 这是正确的方法吗?
谢谢 .
5 回答
AsyncTask
实例只能使用一次 .相反,只需像
new MyAsyncTask().execute("");
一样调用您的任务来自AsyncTask API文档:
线程规则
此类必须遵循一些线程规则才能正常工作:
必须在UI线程上创建任务实例 .
必须在UI线程上调用
execute(Params ...) .
不要手动调用onPreExecute(),onPostExecute(Result),doInBackground(Params ...),onProgressUpdate(Progress ...) .
The task can be executed only once (an exception will be thrown if a second execution is attempted.)
在Steve Prentice的回答中详细说明了ASyncTask发生故障的实例 - 但是,当您执行ASyncTask的次数受到限制时,您可以在线程运行时自由地执行您喜欢的操作 . .
将可执行代码放在doInBackground()中的循环中,并使用并发锁来触发每次执行 . 您可以使用publishProgress()/ onProgressUpdate()检索结果 .
Example:
当然,这比传统的ASyncTask使用稍微复杂一点,并且您放弃使用publishProgress()进行实际的进度报告 . 但是如果你担心内存,那么这种方法将确保在运行时只有一个ASyncTask保留在堆中 .
我遇到过同样的问题 . 在我的情况下,我有一个任务,我想在
onCreate()
和onResume(
) . 所以我使我的Asynctask静态,并从中获取实例 . 现在我们仍然有同样的问题 .所以我在onPostExecute()中做的是这样的:
请记住,我检查静态getInstance方法,我的实例不为null,否则我创建它:
postExecute中的方法将清空实例并重新创建它 . 当然这可以在课外完成 .
我已将旋转任务设置为静态,然后帮助我在旋转更改时附加,分离并重新连接到UI线程 . 但是回到你的问题,我所做的是创建一个标志来查看线程是否正在运行 . 如果要重新启动线程,我会检查旋转任务是否正在运行,如果它是我举报警告 . 如果不是,我将其设为null然后创建一个新的,它将解决您看到的错误 . 此外,在成功完成后,我将完成的旋转感知任务归零,以便它可以再次运行 .
是的,这是真的,医生说只能执行一个Asyntask .
每次你需要使用它时你必须实例: