Android_AsyncTask异步任务机制
今天我们学习了 AsyncTack, 这是一个异步任务。
那么这个异步任务可以干什么呢?
因为只有UI线程,即主线程可以对控件进行更新操作。好处是保证UI稳定性,避免多线程对UI同时操作。
同时要把耗时任务放在非主线程中执行,否则会造成阻塞,抛出无响应异常。
那么在Android中实现异步任务机制有两种方式,Handler和AsyncTask。今天主要讲的是 asyncTack.
我们通过API 来学习下 整个 AsyncTack
一、结构
继承关系
public abstract class AsyncTask extends Object
java.lang.Object
android.os.AsyncTask <params,Progress,Result>
二、类概述
AsyncTask 能够适当的,简单的用于 UI 线程。这个类不需要操作线程(Thread)就可以完成后台操作将结果返回 UI
异步任务的定义是一个在后台线程上运行,其结果是在UI线程上发布的计算。
异步任务被定义成
三种泛型类型:
Params:启动任务执行的输入参数。
Progress:后台人数执行的百分比
Result:后台计算的结果类型
注:在一个异步任务中,不是所有的类型总被用。假如一个类型不被使用,可以简单地使用void 类型。
四个步骤:
1.onPreExecute():在UI线程上调用任务后立即执行。这步通常被用于设置任务,例如在用户界面显示一个进度条。
2.doInBackground(Params...):后台线程执行 onPreExecute()完成立即调用,这步被用于执行较长时间的后台计算。异步任务的参数也被传到这步。计算的结果必须在这步返回,将返回到上一步。在执行过程中可以调用 publishProgress(Progress...)来更新人无语的进度。
3.onProcessProgress():一次呼叫 publishProgress(Progress...)后调用UI线程。执行时间是不确定的。这个方法用于当后台计算还在进行时在用户界面显示进度。例如:这个方法可以被用于一个进度条动画或在文本域显示记录。
4.onPostExecute(Resule):当后台计算结束时,调用 UI线程。后台计算结果作为一个参数传递到这步。
接下来我们用一个栗子看看这个 AsyncTask 到底能做什么。
这是我们的xml 布局文件
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="com.example.multithreadind01.MainActivity" > <TextView
android:id="@+id/textView1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/hello_world" /> <Button
android:id="@+id/button1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_alignTop="@+id/textView1"
android:layout_marginRight="53dp"
android:text="Button" /> <ListView
android:id="@+id/listView1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="@+id/button1"
android:layout_marginTop="84dp" >
</ListView> <ProgressBar
android:id="@+id/progressBar1"
style="?android:attr/progressBarStyleHorizontal"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignLeft="@+id/listView1"
android:layout_alignRight="@+id/button1"
android:layout_below="@+id/button1"
android:layout_marginTop="28dp" /> </RelativeLayout>
这是我们listView xml 的布局文件
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="horizontal" >
<TextView
android:id="@+id/username"
android:layout_weight="1"
android:layout_width="match_parent"
android:layout_height="60dp"
android:textSize="45dp"
/> <TextView
android:id="@+id/sex"
android:layout_weight="1"
android:layout_width="match_parent"
android:layout_height="60dp"
android:textSize="45dp"
/>
</LinearLayout>
这是我们的 user.class
package com.example.multithreadind01;
public class User {
private String username;
private String sex;
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public String getSex() {
return sex;
}
public void setSex(String sex) {
this.sex = sex;
}
}
MainActivity.class
package com.example.multithreadind01; import java.util.ArrayList;
import java.util.List; import android.app.Activity;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.Button;
import android.widget.ListView;
import android.widget.TextView; public class MainActivity extends Activity { private String fromDb_str1 = "";
private Button btn;
private TextView tv;
private ListView lv;
private BaseAdapter adapter;
private List<User> userList = new ArrayList<User>(); @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main); //模拟数据访问产生数据
for (int i = 0; i < 5; i++) {
User u = new User();
u.setUsername("小明"+i);
u.setSex("女"+i);
userList.add(u);
} tv =(TextView)findViewById(R.id.textView1);
btn =(Button)findViewById(R.id.button1);
btn.setOnClickListener(new OnClickListener() { @Override
public void onClick(View v) {
MyTask mt = new MyTask(MainActivity.this);
mt.execute(userList,adapter);//里面的参数是传给doInBackground
/*
Thread t1 = new Thread(new Runnable() {
@Override
public void run() {
fromDb_str1 = "测试";
}
});
t1.start();
tv.setText(fromDb_str1);
*/ }
});
adapter = new BaseAdapter(){ @Override
public int getCount() {
// TODO Auto-generated method stub
return userList.size();
} @Override
public View getView(int position, View convertView, ViewGroup parent) {
LayoutInflater inflater = MainActivity.this.getLayoutInflater();
View view;
if (convertView==null){
view = inflater.inflate(R.layout.item, null);
}
else{
view = convertView;
} TextView tv_username = (TextView)view.findViewById(R.id.username);
TextView tv_sex = (TextView)view.findViewById(R.id.sex);
tv_username.setText(userList.get(position).getUsername());
tv_sex.setText(userList.get(position).getSex());
return view;
} @Override
public Object getItem(int position) {
// TODO Auto-generated method stub
return null;
} @Override
public long getItemId(int position) {
// TODO Auto-generated method stub
return 0;
}
};
lv = (ListView)findViewById(R.id.listView1);
lv.setAdapter(adapter);
}
}
最后是我们异步类 MyTask.class
package com.example.multithreadind01; import java.util.List; import android.os.AsyncTask;
import android.view.View;
import android.widget.BaseAdapter;
import android.widget.ProgressBar;
import android.widget.TextView;
import android.widget.Toast; public class MyTask extends AsyncTask { private BaseAdapter adapter;
private List<User> userList;
private MainActivity activity;
public MyTask(MainActivity activity){
this.activity = activity;
} //1.所有耗时的代码,写到这里来(数据库、蓝牙、网络服务)
//2.绝对不能碰UI
@Override
protected Object doInBackground(Object... params) { userList = (List<User>) params[0];
adapter = (BaseAdapter) params[1];
for (int i = 0; i < userList.size(); i++) {
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
userList.get(i).setUsername("小红"+i);
userList.get(i).setSex("男"+i);
publishProgress(i);
} //userlist,adapter //返回给前端
return "天气:22度";
} //准备
@Override
protected void onPreExecute() {
Toast.makeText(activity, "hello ,今晚约不约", Toast.LENGTH_SHORT).show(); } //做完后执行
@Override
protected void onPostExecute(Object result) {
String r = result.toString();
TextView tv = (TextView)activity.findViewById(R.id.textView1);
tv.setText("访问完成!"+r); } //分步完成
@Override
protected void onProgressUpdate(Object... values) { //0,1,2,3,4
int bar = Integer.parseInt(values[0].toString());
bar = (bar+1)*20;
ProgressBar progressBar = (ProgressBar)activity.findViewById(R.id.progressBar1);
progressBar.setProgress(bar);
adapter.notifyDataSetChanged();
} }
以上案例使我们做到后台数据加载到前端的过程中,使用异步,不会出现所谓的“卡顿”。使得整个程序运行的效果是畅通的,用户体验性也提高。



Android_AsyncTask异步任务机制的更多相关文章
- Android异步任务机制之AsycTask
在Android中实现异步任务机制有两种方式,Handler和AsyncTask. 本篇就说说AsyncTask的异步实现. 1.什么时候使用 AsnyncTask 在上一篇文章已经说了,主线程主要负 ...
- Android异步消息处理机制
安卓子线程无法直接更改UI,所以需要异步消息处理机制来解决 <?xml version="1.0" encoding="utf-8"?><Li ...
- Android 异步消息处理机制解析
Android 中的异步消息处理主要由四个部分组成,Message.Handler.MessageQueue.Looper.下面将会对这四个部分进行一下简要的介绍. 1. Message: Messa ...
- Android多线程----异步消息处理机制之Handler详解
[声明] 欢迎转载,但请保留文章原始出处→_→ 生命壹号:http://www.cnblogs.com/smyhvae/ 文章来源:http://www.cnblogs.com/smyhvae/p/ ...
- 【译】深入理解python3.4中Asyncio库与Node.js的异步IO机制
转载自http://xidui.github.io/2015/10/29/%E6%B7%B1%E5%85%A5%E7%90%86%E8%A7%A3python3-4-Asyncio%E5%BA%93% ...
- 【转】Android 异步消息处理机制 让你深入理解 Looper、Handler、Message三者关系
转载请标明出处:http://blog.csdn.net/lmj623565791/article/details/38377229 ,本文出自[张鸿洋的博客] 很多人面试肯定都被问到过,请问Andr ...
- Android开发之异步消息处理机制AsyncTask
转自:Android AsyncTask完全解析,带你从源码的角度彻底理解 另外一篇比较详细的博文:http://blog.csdn.net/liuhe688/article/details/6532 ...
- Android线程与异步消息处理机制
在程序开发时,对于一些比较耗时的操作,我们通常会为其开辟一个单独的线程来执行,这样可以尽可能的减少用户等待的时间.在Android中,默认情况下,所有的操作都是在主线程中进行的,这个主线程负责管理与U ...
- Android Learning:多线程与异步消息处理机制
在最近学习Android项目源码的过程中,遇到了很多多线程以及异步消息处理的机制.由于之前对这块的知识只是浅尝辄止,并没有系统的理解.但是工程中反复出现让我意识到这个知识的重要性.所以我整理出这篇博客 ...
随机推荐
- mySql事务_ _Java中怎样实现批量删除操作(Java对数据库进行事务处理)?
本文是记录Java中实现批量删除操作(Java对数据库进行事务处理),在开始之前先来看下面这样的一个页面图: 上面这张图片显示的是从数据库中查询出的出租信息,信息中进行了分页处理,然后每行的前面提 ...
- Could not find com.android.tools.build:gradle:1.3.0.
* What went wrong: A problem occurred configuring project ':TZYJ_Android'.> Could not re ...
- Java 技术文章摘录
sokcet 编程实例 android bundle类 Android -- Looper.prepare()和Looper.loop() —深入版 Java NIO系列教程 XML操作 Androi ...
- 使用Dapper读取Oracle多个结果集
Dapper对SQL Server支持很好,但对于Oracle有些用法不一样,需要自己进行特殊处理. 1.首先要自定义一个Oracle参数类 public class OracleDynamicPar ...
- ubuntu14.04 JDK安装
JDK7 安装 1 sudo apt-get install openjdk-7-jdk 2 设置安装环境 在/etc/profile中追加: # Java support # export JAVA ...
- Mybatis 批量更新 ORA-00911: 无效字符的错误
使用<foreach></foreach> 批量insert时报错 ORA-00911: 无效字符的错误 <foreach collection="list&q ...
- css3画三角形的原理
以前用过css3画过下拉菜单里文字后面的“下拉三角符号”,类似于下面这张图片文字后面三角符号的效果 下面是一个很简单的向上的三角形代码 #triangle-up { width: 0; height: ...
- Mybatis获取插入记录的自增长ID(转)
1.在Mybatis Mapper文件中添加属性“useGeneratedKeys”和“keyProperty”,其中keyProperty是Java对象的属性名,而不是表格的字段名. <ins ...
- 尚学堂Spring视频教程(二):Spring控制反转
用Spring来实现IOC 在上节中我们自定义了一个接口BeanFactory和类ClassPathXmlApplicationContext来模拟Spring,其实它们在Spring中确实是存在的, ...
- GNU/Linux复习笔记(2)
---IO重定向: 典型的冯诺依曼计算机由5大部件组成:运算器,控制器,存储器,输入设备和输出设备.而一台计算机上可能有很多输入设备和输出设备,键盘.麦克风是输入设备,显示器.声卡是输出设备,网卡.硬 ...