AsyncTask的使用半解--!

AsyncTask,即异步任务,是Android给我们提供的一个处理异步任务的类.通过此类,可以实现UI线程和后台线程进行通讯,后台线程执行异步任务,并把结果返回给UI线程.

.为什么需要使用异步任务?

我们知道,Android中只有UI线程,也就是主线程才能进行对UI的更新操作,而其他线程是不能直接操作UI的.这样的好处是保证了UI的稳定性和准确性,避免多个线程同时对UI进行操作而造成UI的混乱.但Android是一个多线程的操作系统,我们总不能把所有的任务都放在主线程中进行实现,比如网络操作,文件读取等耗时操作,如果全部放到主线程去执行,就可能会造成后面任务的阻塞.Android会去检测这种阻塞,当阻塞时间太长的时候,就会抛出Application Not Responsed(ANR)错误.所以我们需要将这些耗时操作放在非主线程中去执行.这样既避免了Android的单线程模型,又避免了ANR.

.AsyncTask为何而生?

提到异步任务,我们能想到用线程,线程池去实现.确实,Android给我们提供了主线程与其他线程通讯的机制.但同时,Android也给我们提供了一个封装好的组件–AsyncTask.利用AsyncTask,我们可以很方便的实现异步任务处理.AsyncTask可以在子线程中更新UI,也封装简化了异步操作.使用线程,线程池处理异步任务涉及到了线程的同步,管理等问题.而且当线程结束的时候还需要使用Handler去通知主线程来更新UI.而AsyncTask封装了这一切,使得我们可以很方便的在子线程中更新UI.

.构建AsyncTask子类的泛型参数

AsyncTask

public class NewThread2 extends Activity {
    private TextView text1;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        // TODO Auto-generated method stub
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        text1 = (TextView) findViewById(R.id.text1);
        Button btn = (Button) findViewById(R.id.btn1);
        btn.setOnClickListener(new OnClickListener() {

            @Override
            public void onClick(View v) {
                // TODO Auto-generated method stub
                readUrl("https://www.baidu.com");

            }
        });
    }

    public void readUrl(String Url) {
        new AsyncTask<String, Void, String>() {
            // 此方法必须重写,异步执行后台线程需要完成的任务
            @Override
            protected String doInBackground(String... params) {
                try {
                    URL url = new URL(params[0]);
                    URLConnection connection = url.openConnection();
                    InputStream is = connection.getInputStream();
                    InputStreamReader isr = new InputStreamReader(is);
                    BufferedReader bis = new BufferedReader(isr);
                    String Line;
                    StringBuilder builder = new StringBuilder();
                    while ((Line = bis.readLine()) != null) {
                        builder.append(Line);
                    }
                    bis.close();
                    isr.close();
                    is.close();
                    return builder.toString();
                } catch (MalformedURLException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                } catch (IOException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }

                return null;
            }

            // 执行后台耗时操作时前被调用,通常用来完成一些初始化操作
            @Override
            protected void onPreExecute() {
                Log.d("TAG", ">>>>>>>>>>>>>>>>>>>");
                // TODO Auto-generated method stub
                super.onPreExecute();
            }

            // 当doinBackground()完成过后,系统自动调用,并将方法的返
            //回值传给onpostexecute()可运行在主线程操作ui
            @Override
            protected void onPostExecute(String result) {
                // TODO Auto-generated method stub
                text1.setText(result);
                super.onPostExecute(result);
            }

            // doinBackground()方法中调用publishProgress()方法更行任务的执行进度后,就会触发该方法
            @Override
            protected void onProgressUpdate(Void... values) {
                // TODO Auto-generated method stub

                super.onProgressUpdate(values);
            }

            @Override
            protected void onCancelled(String result) {
                // TODO Auto-generated method stub
                super.onCancelled(result);
            }

            @Override
            protected void onCancelled() {
                // TODO Auto-generated method stub
                super.onCancelled();
            }

        }.execute(Url);
    }
}

新启一个线程来读取网站、、、

这里是运行的样子

AsyncTask是基于线程池进行实现的,当一个线程没有结束时,后面的线程是不能执行的.
cancel方法只是将对应的AsyncTask标记为cancelt状态,并不是真正的取消线程的执行.
onCancelled()方法被调用后,onPostExecute(Result result)方法将不再被调用。

.使用AsyncTask的注意事项

① 必须在UI线程中创建AsyncTask的实例.

② 只能在UI线程中调用AsyncTask的execute方法.

③ AsyncTask被重写的四个方法是系统自动调用的,不应手动调用.

④ 每个AsyncTask只能被执行(execute方法)一次,多次执行将会引发异常.

⑤ AsyncTask的四个方法,只有doInBackground方法是运行在其他线程中,其他三个方法都运行在UI线程中,也就说其他三个方法都可以进行UI的更新操作.

详解请看大神博客
http://blog.csdn.net/liuhe688/article/details/6532519

posted @ 2016-04-19 18:29  Tesi1a  阅读(115)  评论(0)    收藏  举报