一分钟理解handler机制

  • 背景

小编昨晚跟同学聊了很久,了解到其面试中的困惑,每当被问handler机制时就不知道怎么去说,哪怕他知道handler的作用。在这里呢,小编就用案例的形式带你深入了解handler。

  • 案例

异步加载图片,在网上随便找了一张图片地址 http://p1.so.qhmsg.com/t01e2b20000369dbd11.jpg

《一分钟理解handler机制》 网上找的图片

  • 核心代码

handler 实现线程间通讯,是因为共享了 looper 的内存,所以 handlerMessage( ) 运行在哪个线程由 looper 决定。而本章 new handler 默认拿的是主线程的 looper,因此运行在主线程。
主线程创建时,消息队列和轮询器对象就会被创建;
主线程中有一个消息轮询器looper,不断检测消息队列中是否有新消息,如果发现有新消息,自动调用此方法,注意此方法是在主线程中运行的;

      Handler handler=new Handler(){ 
           @Override    
            public void handleMessage(Message msg) { 
                 switch (msg.what){   
                       //7.把位图对象显示至imageview      
                        case 1:    
                                iv.setImageBitmap((Bitmap) msg.obj); 
                                break; 
                        case 2:  
                                Toast.makeText(MainActivity.this,"请求失败!",Toast.LENGTH_SHORT).show(); 
                                break;
                    }
            }};

因为网络交互属于耗时操作,如果网速很慢,代码会阻塞,所以网络交互的代码不能运行在主线程;
在子线程中往消息队列里发消息

new Thread(){
@Override
public void run() {
    try {
        //1.下载图片确定网址,将网址封装成url对象
        URL url = new URL("http://p1.so.qhmsg.com/t01e2b20000369dbd11.jpg");

        //2.获取客户端与服务器连接对象,此时还没有建立连接
        HttpURLConnection conn = (HttpURLConnection) url.openConnection();

        //3.对连接对象进行初始化

           conn.setRequestMethod("GET");//连接方式
           conn.setConnectTimeout(3000);//连接超时
           conn.setReadTimeout(3000);//读取超时

        //4.发送请求,与服务器建立连接
        conn.connect();

        //响应码=200,说明请求成功
        if (conn.getResponseCode()==200){

            //5.获取服务器响应头里的流,流中的数据就是请求端的数据
            InputStream is = conn.getInputStream();

            //6.读取数据流里的数据,构造成位图对象
            Bitmap bitmap = BitmapFactory.decodeStream(is);

            Message msg=handler.obtainMessage();
            //消息对象可以携带数据
            msg.obj=bitmap;
            msg.what=1;
            //把消息发送至主线程的消息队列
            handler.sendMessage(msg);
    }else {
            Message msg = handler.obtainMessage();
            msg.what=2;
            handler.sendMessage(msg);
        }
    } catch (Exception e) {
        e.printStackTrace();
    }
}}.start();
  • 编译后截图

《一分钟理解handler机制》 手机截图

  • 总结

其实handler机制很简单,一般就是用于主线程跟子线程之间的通信。比如,子线程不能更新UI,那么通过handler的sendMessage( )发送消息给主线程,而主线程在创建时,Message Queue(消息队列)和looper(轮询器对象)就会被创建,message就会放在Message Queue里,而Looper一旦发现Message Queue中有消息,就会把消息取出,然后把消息扔给Handler对象,Handler会调用自己的handleMessage方法来处理这条消息。

    原文作者:Trap_余生
    原文地址: https://www.jianshu.com/p/86ea1c817fff
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞