美文网首页
消息机制

消息机制

作者: android小菜鸡一枚 | 来源:发表于2018-08-16 11:02 被阅读0次

Android的消息机制是指Handler的运行机制以及Handler所附带的MessageQueue和Looper的工作过程。Handler的主要作用是将一个任务切换到某个指定的线程中去执行。
Android规定访问UI只能在主线程中进行,如果在子线程中访问UI,那么程序就会抛出异常。

主线程即UI线程,它就是ActivityThread,ActivityThread被创建时就会初始化Looper,这也是主线程中默认可以使用Handler的原因。

Handler运行机制

1.Handler创建时会采用当前线程的Looper来构建内部的消息循环系统,Handler通过ThreadLocal来获取当前线程的Looper,ThreadLocal作用是可以在每个线程中存储数据;
2.Handler创建完毕后,这个时候其内部的Looper以及MessageQueue就可以和Handler一起协同工作了,通过Handler的post方法将一个Runnable投递到Handler内部的Looper中去处理,也可以通过Handler的send方法发送一个消息,这个消息同样会在Looper中处理;
3.当Handler的send方法被调用时,它会调用MessageQueue的enqueueMessage方法将这个消息放入消息队列,Looper发现有新消息到来时,就会处理这个消息,最终消息中的Runnable或者Handler的handleMessage方法就会被调用。
4.Looper是运行在创建Handler所在的线程中,这样Handler中的业务逻辑会被切换到创建Handler所在的线程中去执行了。

ThreadLocal的工作机制

ThreadLocal是一个线程内部的数据存储类,通过它可以在指定的线程中存储数据,数据存储之后,只有在指定线程中可以获取到存储的数据,对于其他线程来说则无法获取到数据。
使用场景:android源码中会使用如Looper,ActivityThread,AMS中都用到了ThreadLocal还有就是复杂逻辑下的对象传递,比如监听器的传递。

消息队列的工作原理

MessageQueue主要包含两个操作,插入和读取分别对应enqueueMessage
和next,enqueueMessage的作用是往消息队列中插入一条消息,而next的作用是从消息队列中取出一条消息并将其从消息队列中移除。它是通过一个单链表的数据结构来维护消息列表。

Looper的工作原理

消息循环,它会不停地从MessageQueue中查看是否有新消息,如果有新消息就会立刻处理,否则就一直阻塞在那里。
通过Looper.prepare()即可以为当前线程创建一个Looper,接着通过Looper.loop()来开启消息循环。

new Thread("Thread#2"){
    @Override
    public void run(){
        Looper.prepare();
        Handler handler = new Handler();
        Looper.loop();
    }
}

Looper除了prepare方法外,还提供了prepareMainLooper方法,这个方法主要是给主线程也就是ActivityThread创建Looper使用的,其本质也是通过prepare方法来实现的。Looper提供了getMainLooper方法,通过它可以在任何地方获取到主线程的Looper,Looper也可以退出,提供了quit和quitSafely方法。
Looper的loop方法是一个死循环,唯一跳出循环的方式是MessageQueue的next方法返回了null;当Looper的quit方法被调用时,Looper就会调用MessageQueue的quit或者quitSafely方法来通知消息队列退出,当消息队列被标记为退出状态时,它的next方法就会返回null。
loop方法会调用MessageQueue的next方法来获取新消息,而next是一个阻塞操作,当没有消息时,next方法会一直阻塞在那,这也导致了loop方法一直阻塞在那。

主线程的消息循环

Android的主线程就是ActivityThread,主线程的入口方法为main,在main方法中系统会通过Looper.prepareMainLooper()来创建主线程的Looper以及MessageQueue,并通过Looper.loop()来开启主线程的消息循环。
主线程的消息循环开始了以后,ActivityThread还需要一个Handler来和消息队列进行交互,这个Handler就是ActivityThread.H,它内部定义了一组消息类型,主要包括了四大组件的启动和停止过程。
ActivityThread通过ApplicationThread和AMS进行进程间通信,AMS以进程间通信的方式完成ActivityThread的请求后会回调ApplicationThread中的Binder方法,然后ApplicationThread会向H发送
消息,H接收消息后会将ApplicationThread中的逻辑切换到ActivityThread中去执行,即切换到主线程中去执行,这个过程就是主线程的消息循环模型。

消息机制的原理

在子线程执行完耗时操作,Handler通过sendMessage发送消息后,会调用MessageQueue.enqueueMessage方法向消息队列中添加消息,然后Looper调用loop()方法开启循环后会不断地从消息队列中读取消息,然后调用目标Handler的dispatchMessage方法传递消息,然后回到Handler所在线程,目标Handler收到消息,调用handleMessage方法,接收消息,处理消息。


image.png
image.png

MessageQueue,Handler和Looper三者之间的关系

每个线程中只能存在一个Looper,Looper是保存在ThreadLocal中的。主线程(UI线程)已经创建了一个Looper,所以在主线程中不需要再创建Looper,但是在其他线程中需要创建Looper。每个线程中可以有多个Handler,即一个Looper可以处理来自多个Handler的消息。 Looper中维护一个MessageQueue,来维护消息队列,消息队列中的Message可以来自不同的Handler。

《Android开发艺术探讨》Android的消息机制

相关文章

  • Runtime

    相关简单介绍 消息机制消息传递机制消息转发机制-动态添加方法消息转发机制-快速转发消息转发机制-慢速转发消息转发机...

  • <> Chapter 10

    Android的消息机制 Android消息机制概述 Android的消息机制主要是指Handler的运行机制以及...

  • iOS消息转发机制

    消息转发机制: 消息转发机制是相对于消息传递机制而言的。 1、消息(传递)机制 RunTime简称运行时。就是系统...

  • OC消息机制,消息转发机制

    Runtime简称运行时,其中最主要的是消息机制 概述 C 与 OC 的不同 1.C 语言,函数的调用在编译的时候...

  • Runtime 你为何如此之屌?

    一、消息驱动机制 消息驱动机制: 运行的时候的一些机制,最主要的是消息机制。 消息驱动机制-动态调用过程 : 对于...

  • 08.Objective-C 消息机制

    问题 消息机制的三个阶段 1.消息机制发送消息阶段-消息发送2.消息机制动态方法解析阶段 -动态解析3.消息机制消...

  • 关于runtime的一些简单理解

    1.消息发送OC:运行时机制,消息机制是运行时机制最重要的机制消息机制:任何方法调用,本质都是发送消息 SEL:方...

  • runtime系列文章总结

    《iOS Runtime详解(消息机制,类元对象,缓存机制,消息转发)》《消息转发机制与Aspects源码解析》《...

  • 消息机制

    消息机制 主线程创建后Looper.prepare创建lopper对象,创建looper的同时或创建消息队列mes...

  • 消息机制

    阻塞/非阻塞;同步/非同步的概念往往不会分开说,经常会将他们组合到一起,比如:同步阻塞 或 同步非阻塞。 具体解析...

网友评论

      本文标题:消息机制

      本文链接:https://www.haomeiwen.com/subject/adibmftx.html