博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Android AsyncTask 的实现及 cancel 方式
阅读量:5071 次
发布时间:2019-06-12

本文共 3670 字,大约阅读时间需要 12 分钟。

最近做一个功能需要用到AsyncTask。实现的过程很容易,但是在cancel的时候遇到了一点麻烦。找了很多地方终于找到了比较好的方法,这里跟大家分享一下。


根据Android Developer的介绍 :

AsyncTask enables proper and easy use of the UI thread. This class allows to perform background operations and publish results on the UI thread without having to manipulate threads and/or handlers.

AsyncTask其实是Android给开发者提供的一个简单轻量级的多线程类,通过它我们可以很容易新建一个线程做一些耗时的操作,并在这个过程中更新UI。之所以说它轻量级,是因为缺少了直接使用Thread的灵活性。如果是很复杂的操作,还是建议通过Thread来操作,然后通过Broadcast的方式来更新UI。

使用AsyncTask的时候还需要注意,如果AsyncTask在运行过程中使用了某个activity,那么我们就需要在保证AsyncTask的运行过程中这个activity不被destory,或者是在activity的onDestory()方法里面cancel掉这个AsyncTask。但是,如果是一直不让activity被destory的话,相当于不让用户切换界面,这个体验其实时不好的。所以,我们最好使用ProgressDialog,让用户知道我们在努力完成他们的操作,为了让用户可以cancel这个操作,我们可以检测ProgressDialog有没有取消,如果取消了,那就cancel整个AsyncTask。

所以,我们总是会需要cancel AsyncTask。这里贴一段我写的代码,有点点改动。

AsyncTask
1     private class OpenWebPortalTask extends AsyncTask
{ 2 private static final String DEFAULT_URL = "https://www.google.com"; 3 private ProgressDialog mProgressDialog = null; 4 private Activity mActivity; 5 6 public OpenWebPortalTask(Activity activity){ 7 mActivity = activity; 8 mProgressDialog = new ProgressDialog(mActivity); 9 mProgressDialog.setMessage(getString(R.string.open_aweb_portal));10 mProgressDialog.setCancelable(true);11 mProgressDialog.setOnCancelListener(new DialogInterface.OnCancelListener() {12 13 @Override14 public void onCancel(DialogInterface dialog) {15 cancel(true);16 }17 });18 }19 20 @Override21 protected void onPreExecute(){22 mProgressDialog.show();23 }24 25 @Override26 protected Void doInBackground(Void... params) {27 String schemeUrl = PropertyMgr.getInstance().getPortalURI();28 if (TextUtils.isEmpty(schemeUrl)) {29 schemeUrl = DEFAULT_ANTI_THEFT_URL;30 }31 try {32 String st = CredentialManager.getInstance().getServiceTicket();33 if(st != null) {34 schemeUrl += "?st=" + st;35 }36 } catch (Exception e) {37 SymLog.e(TAG, "Get Service Ticket failed.");38 }39 if(isCancelled()) {40 return null;41 }42 Intent i = new Intent(Intent.ACTION_VIEW);43 i.setData(Uri.parse(schemeUrl));44 startActivity(i);45 return null;46 }47 48 @Override49 protected void onPostExecute(Void v) {50 mActivity.runOnUiThread(new Runnable() {51 @Override52 public void run() {53 if (mProgressDialog != null) {54 mProgressDialog.dismiss();55 mProgressDialog = null;56 }57 }58 });59 }60 }

这段代码里面,

String st = CredentialManager.getInstance().getServiceTicket();

 是个耗时操作,所以需要放在AsyncTask里面。例子中,在onPreExecute中显示ProgressDialog,在onPostExecute中销毁。

注意cancel AsyncTask的方法:

  1. 在ProgressDialog的setOnCancelListener里调用cancel(true);,表示如果ProgressDialog被cancel的话,也cancel掉AsyncTask;
  2. 在doInBackgroud方法中,判断isCancelled()是否为真,如果真,那么就返回。

为什么在doInBackgroud中判断?因为AsyncTask的重要工作都是在doInBackgroud中完成,它如果退出了,那么就意味着AsyncTask将被销毁了。

具体在doInBackgroud的哪部分判断是否要退出呢?这就需要根据程序的逻辑。一般在耗时操作的后面加上判断!代码中可以根据需要加多个这样的判断。


 

AsyncTask用于实现一些简单的多线程任务确实非常简单和好用,希望对大家有所帮助。

转载于:https://www.cnblogs.com/wangfenjin/archive/2012/09/21/2696905.html

你可能感兴趣的文章
Scrapy实战篇(三)之爬取豆瓣电影短评
查看>>
HDU 5510 Bazinga KMP
查看>>
[13年迁移]Firefox下margin-top问题
查看>>
Zookeeper常用命令 (转)
查看>>
【CF888E】Maximum Subsequence 折半搜索
查看>>
Java程序IP v6与IP v4的设置
查看>>
RUP(Rational Unified Process),统一软件开发过程
查看>>
eclipse下的tomcat内存设置大小
查看>>
数据库链路创建方法
查看>>
linux文件
查看>>
Linux CentOS6.5上搭建环境遇到的问题
查看>>
Enterprise Library - Data Access Application Block 6.0.1304
查看>>
重构代码 —— 函数即变量(Replace temp with Query)
查看>>
vmware tools 的安装(Read-only file system 的解决)
查看>>
Bootstrap栅格学习
查看>>
程序员的数学
查看>>
聚合与组合
查看>>
数据库图片存储也读取
查看>>
jQuery如何获得select选中的值?input单选radio选中的值
查看>>
粘贴板工具,剪切板工具
查看>>