AsyncTask专题之一 为啥要使用AsyncTask
2016-07-10 13:37
211 查看
验证一、尝试在UI线程中做耗时操作。
在UI线程中输出100个数,存放到TextView中,每sleep 会儿就存一个
演示代码如下:
一会儿就报错了,
ANR(application not response)应用程序无响应
结论:在UI线程中不能进行耗时操作
验证二、尝试在子线程中进行耗时操作,并更新UI
在xml文件中添加一个按钮,当点击按钮的时候,启动子线程,循环100个数字,每5秒更新一次
TextView
代码如下所示:
XML布局:
验证代码:把验证一的代码注释掉了
关于线程启动的方式,这里如果小伙伴忘了可以看下:
1.继承Thread类
class A extends Thread{
//重写run()方法
}
A a = new A();
a.start();
2.实现runnable接口
class B extends implement Runnable{
//重写run()方法
}
B b = new B();
new Thread(b).start();
报错,异常信息如下所示:
结论:只能在UI线程中去更新UI
那么既然UI线程中不能去做耗时操作,而子线程中可以做耗时操作,但子线程中又不能更新UI怎么办呢?
答曰:可以使用AsyncTask (不会念不要紧,I think task哈哈~~)
在UI线程中输出100个数,存放到TextView中,每sleep 会儿就存一个
演示代码如下:
package com.yztc.day0710_wang_02; import android.support.v7.app.AppCompatActivity; import android.os.Bundle; import android.util.Log; import android.widget.TextView; public class MainActivity extends AppCompatActivity { private TextView mTextView; public static final String TAG = "MainActivity"; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); mTextView = (TextView) findViewById(R.id.tv_show); //Thread方法中,可以使用currentThread()获得线程对象 //使用getId()获得线程id,使用getName()获得线程名字 Log.d(TAG,"当前线程的id" + Thread.currentThread().getId() + ",当前线程的名字:" + Thread.currentThread().getName()); for(int i = 0;i < 100;i ++){ try { Thread.sleep(5000); } catch (InterruptedException e) { e.printStackTrace(); } //setText中的参数要求是charsequences ,i 是一个int,加上一个""就转为字符序列 mTextView.setText(i + ""); } } }
一会儿就报错了,
ANR(application not response)应用程序无响应
E/ActivityManager: ANR in com.yztc.day0710_wang_02 (com.yztc.day0710_wang_02/.MainActivity) Reason: keyDispatchingTimedOut Load: 0.54 / 0.4 / 0.16 CPU usage from 28445ms to 0ms ago:
结论:在UI线程中不能进行耗时操作
验证二、尝试在子线程中进行耗时操作,并更新UI
在xml文件中添加一个按钮,当点击按钮的时候,启动子线程,循环100个数字,每5秒更新一次
TextView
代码如下所示:
XML布局:
<?xml version="1.0" encoding="utf-8"?> <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.yztc.day0710_wang_02.MainActivity"> <TextView android:id="@+id/tv_show" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="Hello World!"/> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_below="@id/tv_show" android:text="启动子线程" android:onClick="onStartSubThread"/> </RelativeLayout>
验证代码:把验证一的代码注释掉了
关于线程启动的方式,这里如果小伙伴忘了可以看下:
1.继承Thread类
class A extends Thread{
//重写run()方法
}
A a = new A();
a.start();
2.实现runnable接口
class B extends implement Runnable{
//重写run()方法
}
B b = new B();
new Thread(b).start();
package com.yztc.day0710_wang_02; import android.os.Bundle; import android.support.v7.app.AppCompatActivity; import android.util.Log; import android.view.View; import android.widget.TextView; public class MainActivity extends AppCompatActivity { private TextView mTextView; public static final String TAG = "MainActivity"; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); mTextView = (TextView) findViewById(R.id.tv_show); //Thread方法中,可以使用currentThread()获得线程对象 //使用getId()获得线程id,使用getName()获得线程名字 Log.d(TAG, "当前线程的id" + Thread.currentThread().getId() + ",当前线程的名字:" + Thread.currentThread().getName()); // for (int i = 0; i < 100; i++) { // try { // Thread.sleep(5000); // } catch (InterruptedException e) { // e.printStackTrace(); // } // //setText中的参数要求是charsequences ,i 是一个int,加上一个""就转为字符序列 // mTextView.setText(i + ""); // } } //响应按钮事件 public void onStartSubThread(View view) { new Thread(){ @Override public void run() { super.run(); Log.d(TAG,"子线程的id=" + Thread.currentThread().getId() + ",子线程的名称=" + Thread.currentThread().getName()); for (int i = 0;i < 100;i ++){ try { Thread.sleep(5000); } catch (InterruptedException e) { 9cb8 e.printStackTrace(); } mTextView.setText("" + i); } } }.start(); } }
报错,异常信息如下所示:
E/AndroidRuntime: FATAL EXCEPTION: Thread-86 android.view.ViewRootImpl$CalledFromWrongThreadException: Only the original thread that created a view hierarchy can touch its views.
结论:只能在UI线程中去更新UI
那么既然UI线程中不能去做耗时操作,而子线程中可以做耗时操作,但子线程中又不能更新UI怎么办呢?
答曰:可以使用AsyncTask (不会念不要紧,I think task哈哈~~)
相关文章推荐
- Android AsyncTask源码分析
- Android中异步类AsyncTask用法总结
- Android中AsyncTask的用法实例分享
- Android的异步任务AsyncTask详解
- Android使用AsyncTask实现多线程下载的方法
- 简介Android 中的AsyncTask
- Android AsyncTask完全解析 带你从源码的角度彻底理解
- Android 中使用 AsyncTask 异步读取网络图片
- Android中通过AsyncTask类来制作炫酷进度条的实例教程
- Android中AsyncTask异步任务使用详细实例(一)
- asynctask的用法详解
- Android中AsyncTask详细介绍
- Android中AsyncTask与handler用法实例分析
- Android通过Handler与AsyncTask两种方式动态更新ListView(附源码)
- 详解Android App中的AsyncTask异步任务执行方式
- Android开发笔记之:AsyncTask的应用详解
- android教程之使用asynctask在后台运行耗时任务
- 详解Android中用于线程处理的AsyncTask类的用法及源码
- 详解Android中AsyncTask机制
- 线程池三:AsyncTask线程池