• android Handler


    一、Handler的作用
    1、Handler的作用是在andorid中实现线程间的通信。我们常说的说的,子线程处理逻辑,主线程更新UI是上述情况的一个子集。

    二、源码分析
    1、Handler源码
    源码地址:http://androidxref.com/7.1.1_r6/xref/frameworks/base/core/java/android/os/Handler.java

    2、具体分析
    创建Handler并消费的过程
    先看下Handler的构造函数的核心部分

    mLooper = Looper.myLooper();
    if (mLooper == null) {
    throw new RuntimeException(
    “Can’t create handler inside thread that has not called Looper.prepare()”);
    }
    mQueue = mLooper.mQueue;
    mCallback = callback;
    mAsynchronous = async;
    Handler在默认构造函数里检查了当前线程是否是Looper线程,如果不是Looper线程就抛出异常。我们常在主线程直接

    new Handler()
    这样做之所以没问题,是因为ActivityThread默认创建了Looper对象。如果我们想在非主线程T里创建Handler对象需显示调用

    Looper.prepare()
    那另外一种构造Handler的方式是

    public Handler(Looper looper, Callback callback, boolean async) {
    mLooper = looper;
    mQueue = looper.mQueue;
    mCallback = callback;
    mAsynchronous = async;
    }
    这种方法要显示的传进一个Looper对象。获取Looper对象的方法是

    thread.getLooper();
    前提是thread线程已经是looper线程,例如HandlerThread线程的对象就是looper线程。
    通过以上2种方法,我们就创建可以创建一个Looper对象,此时可以直接构造一个Handler对象出来,并开启Loop循环

    Looper.loop();//这是一个死循环for(;😉,此循环在线程T里执行
    从构造函数核心部分可知,Handler通过mLooper对象持有了一个MessageQueue对象mQueue。loop循环就是在遍历这个mQueue,当有Message对象msg进入队列的时候,msg会被立刻通过

    mQueue.next();//如果没有消息,会阻塞在这里
    方法被取出,通过

    msg.dispatchMessage();//在线程T里执行
    回调给Handler处理,Handler再通过

    handleMessage();//在线程T里执行
    将消息下发给具体处理业务的逻辑。

    生产的过程
    还是先看一段源码

    private boolean enqueueMessage(MessageQueue queue, Message msg, long uptimeMillis) {
    msg.target = this;
    if (mAsynchronous) {
    msg.setAsynchronous(true);
    }
    return queue.enqueueMessage(msg, uptimeMillis);
    }
    我们在所有其他线程A中,通过Handler的对象sendMessage或者post等方法生产的消息,最终都会通过这里被enqueue到该Handler持有Looper成员变量的MessageQueue成员变量中,enqueue的过程必须加锁,这里就不展开说了。

    上面就是一个生产过程,实现了从线程A中将消息发送到线程T中。

    三、总结
    Handler必须搭配Looper使用,这是因为MessageQuene只有进出的接口,没有loop接口,需要Looper对象拿出消息并回调给Hander对象进行处理。

  • 相关阅读:
    LED显示屏安全亮度参数设置方法和防护
    Mac版本破解Typora,解决Mac安装软件的“已损坏,无法打开。 您应该将它移到废纸篓”问题
    如此简单易懂的方式 让网站支持PWA
    百度飞桨(PaddlePaddle)- 张量(Tensor)
    [单片机框架][device层] fuelgauge 电量计
    【论文阅读】TEMPORAL ENSEMBLING FOR SEMI-SUPERVISED LEARNING
    熊猫电影网站(springboot+ssm+vue+element+shiro+jwt+redis)前后端分离
    npm install常见报错及问题
    怎样才能在网上快速赚到钱?
    ubutun上编译出现undefined reference to symbol ‘dladdr@@GLIBC_2.2.5‘的错误
  • 原文地址:https://blog.csdn.net/cuisidong1997/article/details/134428950