2019-10-31 EventBus的流程---菜鸡
最近真的忙,把身体都搞虚脱了,每天晕乎乎的,感觉只有搞技术的时候才是最舒服的时候,代码才是精神食粮啊,今天闲下来记录下载项目中使用的Eventbusd 流程,可能不是很详细,但是尽最大努力来分析下。
首先我将源码放到source insight中便于编辑。那接下一起看看eventbus的流程源码吧,
直接看红框部分,我特意将代码注释了一下,这个很常见,获取一个Eventbus的单例对象,这也是getdefault方法的用处。
接下来,看看里面注册方法做了什么,我们需要了解怎么注册的,
首先通过反射拿到外部传入的被观察类,注释中注释了,这里用了反射,首先我们看上面我的注释,首先找到被观察类和被观察类的所有方法,然后将类及其方法关联起来,我们一步步来,首先分析1,看看怎么找到所有方法。
可以看到,因为反射的性能不是很高,其中在编译期添加索引方式来提高性能,这是拿到我们外部传入的类的所有方法的过程,我们继续去深入怎么通过反射拿到方法信息,
这是通过反射拿到我们外部传入类中的方法,我先分了五步,我们一步一步来分析每个的作用和流程
首先我们来看1,FindState,这一看,我们大概就能猜测到,这个类是干什么的。对是否找到方法的状态管理。
这个就不多说了,不过这种方式确实值得借鉴。
再来看看3、
简单的赋值,需要注意点是,内部还涉及了我们定义类的继承关系,是否有父类,如果有,是否需要查找父类的方法,这个地方真的妞,不得不感叹做着逻辑思维非常的缜密。
回头继续看4,我们可以知道,首先通过判断外部的类是否已经实例化,如果已经实例化,则执行4和5.我们首先看4.
这里可以看到,涉及到外部我们指定了时间类型和执行的线程,那么到这里有一个疑问就是,eventbus怎么做到切换线程呢?带着这个问题,我们看下面的流程。
关于线程的切换,我们先看事件的发布,发布的时候肯定要指定对应的线程,那么这个时候我们就可以找到怎么去切换线程的。
此处拿到指定线程的状态
这是事件的发布,我们直接看注意这个地方,进入这个方法中查看,这个方法到底做了什么?
其实这个类还没有真正的发布事件,只是获取事件类型,然后交给postsingleForEventType方法执行,那么这个类是做什么的呢?我们大概了解下,这个方法确定当前事件和类是否已经关联起来。
箭头的地方就是我们外部指定的线程,拿到外部指定的线程,然后交给方框中的方法去执行,那么这个是怎么拿到的呢?肯定有这样的疑问,不慌,其实我也有这样的疑问,我们来往上找找,看到加粗的字体哪里,PostingThreadState postingState =currentPostingThreadState.get();,那么这个currentPostingThreadState我们这个时候可以猜的到了,肯定是一个ThreadLocal了,关于这个是干什么的,相信不陌生了,对,就是储存线程中的变量,保持每个线程中的变量不被其他线程所修改,
这就是线程怎么指定去执行的,那么接着看,
框起来的大致类似,我们先看这个红框里面的。
其实看源码,可以知道这些都是线程,其中 BackgroundPoster和AsyncPoster都实现了runable接口,这说明,这两个是在子线程中执行的
果然是这样的
好了,分析发布事件,线程指定,那么怎么接受事件呢?估计没跟着走的时候很可能有这个疑问,好,我来解答下,
就是这个方法,那么这个方法到底是干嘛的呢?知道反射的肯定了解这个方法,invoke方法用来在运行时动态地调用某个实例的方法,实际上也就是说这个方法在jvm底层时已经绑定了subcribe注解的方法,这个时候通过反射获取到当前方法的全部信息,因为我们用了subcribe注解,post事件的时候,我们建一个集合来装在所有带有注解的,通过invoke方法动态的调用每一个带有注解的方法,这就形成了一个完成的事件发送和处理
这里可以从注册的时候可以看出一二来,大致思路是这样的,细微之处就需要我们平时多研究下源码,其实看源码最大的思想是敢于大胆的去猜想,然后想方设法证实自己的猜想