Android的消息机制Handler

android的消息机制——Handler:Handler是一个Android SDK 提供给开发者方便进行异步消息处理的类。

一.为什么用handler
1.消息机制:不同线程之间的通信。那么推出来android的消息机制可以用handler机制来概况.
2.那么android为什么会用到handler机制:避免ANR.
3.避免ANR的方法就是:子线程执行耗时操作,通过handler机制完成UI在主线程的更新.
4.那么为什么子线程不能执行UI:因为UI控件不是线程安全的,那么多线并发对UI进行操作会达到不可预期的结果.
5.那么UI控件为什么不设计为线程安全的:因为设计为线程安全的,首先UI性能低效,其次有种杀鸡焉用牛刀的感觉,UI设计是秉承着简单有效的原则,那么有悖于设计.

二,handler中几个关键的类(Handler、Looper、MessageQueue、Message、ThreadLocal):

 1.从使用角度来说用handler就是:建立handler重写handlermsg方法对消息进行处理,通过线程sendmsg.
 2.Handler特性:
          a.Android里没有全局Message Queue消息队列,每个Activity都有一个独立的消息队列且采用先进先出的原则.不同APK不能通过handle进行消息传递.
   b.每个handler实例都会绑定到创建它的线程中.
   c.handler发送消息到Message Queue中,每个massage发送到消息队列中采用先进先出原则.发送消息采用异步方式不会阻塞线程,而接受消息采用同步方式会阻塞线程,即handler处理完一个mesage消息对象后才会接着去取
      下一个消息进行处理.
    
 3.那么对于几个经常用的类作用如下:
        Handler负责发送和处理消息
        Looper消息泵,将循环取消息将取到的消息交给handler进行处理.没有消息的时候将会处于阻塞状态.
        MessageQueue消息队列,负责存取消息。
        Message具体发送的消息。
        ThreadLocal它主要用于做线程间的数据隔离用的,这里它在每个线程中存放各自对应的Looper。

三.常用handler消息处理例子讲解.
  根据常用的几种handler消息传递使用方式进行讲解.
  首先创建一个activity,在activity实例3个button,分别处理常用的几种类型的handler.

  1.主线程建立handler自用.2.子线程通过Looper.getMainLooper()获取父类的looper建立handler.3.将主线程的handler传递给子线程进行通信.

public class MainActivity extends Activity implements OnClickListener{
    Button mHandlerButton1 = null;
    Button mHandlerButton2 = null;
    Button mHandlerButton3 = null;
    Handler myHandler;
    Message msg;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main1);
        mHandlerButton1 = (Button)findViewById(R.id.handler_button1);
        mHandlerButton1.setOnClickListener(this);
        mHandlerButton2 = (Button)findViewById(R.id.handler_button2);
        mHandlerButton2.setOnClickListener(this);
        mHandlerButton3 = (Button)findViewById(R.id.handler_button3);
        mHandlerButton3.setOnClickListener(this);
    }

    public void onClick(View v){
        if(v == mHandlerButton1){
            myHandler = new MyHandler();
            msg = myHandler.obtainMessage(1,"threadmain handler");
            msg.sendToTarget();
        }else if(v == mHandlerButton2){
            InnerThread innerthread = new InnerThread();
            innerthread.start();
        }else if(v == mHandlerButton3){
            myHandler = new MyHandler();
            MyThread mythread = new MyThread(myHandler);
            mythread.start();
        }
    }
    private class InnerThread extends Thread{
        @Override
        public void run(){
            //myHandler = new MyHandler();//仅能在主线程内采用不带Looper对象创建Hanler对象.此处如果这么用会抛异常
            //myHandler = new MyHandler(Looper.myLooper());//Looper.myLooper获取looper为null
            myHandler = new MyHandler(Looper.getMainLooper());//获取父类的looper可以成功创建handler并发送消息
            msg = myHandler.obtainMessage(2,"InnerThread handler");
            msg.sendToTarget();
        }
    }
    private class MyThread extends Thread{
        private Handler innerHandler; 
        public MyThread(Handler handler){
            this.innerHandler = handler;//通过构造器获取主线程的handler并发送给主线程.
        }
        @Override
        public void run(){
            msg = innerHandler.obtainMessage(3,"MyThread handler");
            msg.sendToTarget();
        }
    }
    public class MyHandler extends Handler{
        public MyHandler(Looper myLooper){
            super(myLooper);
        }
        public MyHandler(){}//
        @Override
        public void handleMessage(Message msg){
            switch(msg.what){
            case 1:
                Log.d("HandlerMessage","this handler is in main thread");
                break;
            case 2:
                Log.d("HandlerMessage","this handler is in InnerThread");
                break;
            case 3:
                Log.d("HandlerMessage","this handler is in MyThread");
                break;
                default:
                 break;
            }
        }
    }
<?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="vertical" >
  <Button
      android:id="@+id/handler_button1"
      android:layout_width="wrap_content"
      android:layout_height="wrap_content"
      android:text="@string/handlerbutton1"/>
  <Button
      android:id ="@+id/handler_button2"
      android:layout_width="wrap_content"
      android:layout_height="wrap_content"
      android:text="@string/handlerbutton2"/>
   <Button
      android:id ="@+id/handler_button3"
      android:layout_width="wrap_content"
      android:layout_height="wrap_content"
      android:text="@string/handlerbutton3"/>
      

</LinearLayout>

从handler特质来看,handler主要异步处理较费时的操作,优先将界面返回给客户,处理完成后进行ui的更新.

猜你喜欢

转载自www.cnblogs.com/syyh2006/p/9172168.html