EventBus源码解析之构造器

前言

EventBus的构造方法涉及到属性的初始化,以及一些重要参数的赋值、重要标志位的获取。

代码分析

1、EventBus构造

EventBus的构造采用单例模式中的双检锁/双重校验锁方式,这种方式是多线程安全的。代码如下所示:

static volatile EventBus defaultInstance;
public static EventBus getDefault() {
    EventBus instance = defaultInstance;
    if (instance == null) {
        synchronized (EventBus.class) {
            instance = EventBus.defaultInstance;
            if (instance == null) {
                instance = EventBus.defaultInstance = new EventBus();
            }
        }
    }
    return instance;
}
/**
     * Creates a new EventBus instance; each instance is a separate scope in which events are     delivered. To use a central bus, consider {@link #getDefault()}.
     */
    public EventBus() {
        this(DEFAULT_BUILDER);
    }

该单例模式的流程图如下所示:

在这里插入图片描述

可以看到具体的构造方法用到了new EventBus(),而与普通的单例模式不同的是构造方法前面用了public修饰。看注释可以知道这是提供给使用者生成多个对象准备的,而且每个对象的使用是互相独立的。当然一般情况下我们只是用getDefault()创建对象就足够了。

2、EventBusBuilder的分析

EventBus的构造方法最终是会调到EventBus(EventBusBuilder builder)这个方法。那么先看下这个方法的代码:

EventBus(EventBusBuilder builder) {
    logger = builder.getLogger();
    subscriptionsByEventType = new HashMap<>();
    typesBySubscriber = new HashMap<>();
    stickyEvents = new ConcurrentHashMap<>();
    mainThreadSupport = builder.getMainThreadSupport();
    mainThreadPoster = mainThreadSupport != null ? mainThreadSupport.createPoster(this) : null;
    backgroundPoster = new BackgroundPoster(this);
    asyncPoster = new AsyncPoster(this);
    indexCount = builder.subscriberInfoIndexes != null ? builder.subscriberInfoIndexes.size() : 0;
    subscriberMethodFinder = new SubscriberMethodFinder(builder.subscriberInfoIndexes,
            builder.strictMethodVerification, builder.ignoreGeneratedIndex);
    logSubscriberExceptions = builder.logSubscriberExceptions;
    logNoSubscriberMessages = builder.logNoSubscriberMessages;
    sendSubscriberExceptionEvent = builder.sendSubscriberExceptionEvent;
    sendNoSubscriberEvent = builder.sendNoSubscriberEvent;
    throwSubscriberException = builder.throwSubscriberException;
    eventInheritance = builder.eventInheritance;
    executorService = builder.executorService;
}

可以看到在构造函数中大量调用builder对象获取配置,EventBusBuilder采用的是建造者模式。而如果通过getDefault()方式获取EventBus对象的话,那么则会用系统默认创建的DEFAULT_BUILDER;

private static final EventBusBuilder DEFAULT_BUILDER = new EventBusBuilder();

那么先分别看下EventBus(EventBusBuilder builder)中配置的意义,这也可以帮助理解后续其他部分代码:

1、三个Poster,用于后续的事件分发。backgroundPoster和asyncPoster直接new出一个对象出来,而mainThreadPoster的获取方式比较特殊,他是通过MainThreadSupport这个接口的内部类来实现的。MainThreadSupport最终也是调用HandlerPoster实现新建Poster的,也就是说MainThreadSupport充当了代理的功能。逻辑图如下所示:

在这里插入图片描述

2、subscriberMethodFinder 这个是注册的时候主要的方法,用于查询对应的Event等信息。

3、subscriberInfoIndexes 该变量为索引参数,用于后续采用索引或者反射的方式查询。

4、eventInheritance 该变量为判断是否考虑父类的情况

由上可知EventBusBuilder在构建的时候起着相当重要的作用。那么着重分析一下EventBusBuilder,先看下EventBusBuilder中定义的变量:

private final static ExecutorService DEFAULT_EXECUTOR_SERVICE = Executors.newCachedThreadPool();

    boolean logSubscriberExceptions = true;
    boolean logNoSubscriberMessages = true;
    boolean sendSubscriberExceptionEvent = true;
    boolean sendNoSubscriberEvent = true;
    boolean throwSubscriberException;
    boolean eventInheritance = true;
    boolean ignoreGeneratedIndex;
    boolean strictMethodVerification;
    ExecutorService executorService = DEFAULT_EXECUTOR_SERVICE;
    List<Class<?>> skipMethodVerificationForClasses;
    List<SubscriberInfoIndex> subscriberInfoIndexes;
    Logger logger;
    MainThreadSupport mainThreadSupport;

再看下EventBusBuilder与其他类的被调用关系图如下所示:

EventBusBuilder被调用逻辑图

OK,从上面的逻辑图可以看出EventBusBuilder在构造方法的时候提供参数配置的同时也提供了两个比较重要的功能:一个是newCachedThreadPool线程池,可用于AsyncExecutor调用。另一个就是installDefaultEventBus(),他用于重新注册默认的builder,他只能在获取对象之前调用,代码如下所示。

public EventBus installDefaultEventBus() {
        synchronized (EventBus.class) {
            if (EventBus.defaultInstance != null) {
                throw new EventBusException("Default instance already exists." +
                        " It may be only set once before it's used the first time to ensure consistent behavior.");
            }
            EventBus.defaultInstance = build();
            return EventBus.defaultInstance;
        }
    }

总结

1、首先通过Eventbus的构造过程可以了解后续注册以及事件方法所要用到的几个属性,对于功能会有个大概的预先了解。

2、MainThreadSupport以及EventBusBuilder的写法还不是特别理解。这边先过一遍,后续再深入理解。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值