1、EventBus理论基础
目标:进程内解耦。
总共四部分:
1.1、创建事件
EventBus类,是guava中消息发布和订阅的类,即订阅者通过EventBus注册并订阅事件,发布者将事件发送至EventBus中,EventBus将事件顺序的通知给时间订阅者,所以,这里有一个特别重要的注意点:事件处理器必须迅速处理完事件,否则可能会导致事件堆积。
EventBus eventBus = new EventBus();
/**
* 带参数,作用:仅仅作为标识
*/
EventBus eventBus = new EventBus(TradeAccountEvent.class.getName());
1.2、创建监听
监听类,即订阅类:
定义规则:
1)public修饰的
2)参数个数为1,
3)参数类型和订阅事件类型一致。
4)方法上增加注解:@Subscribe
1.3、订阅事件
调用EventBus的register方法完成注册。
1.4、发布事件
调用EventBus.post方法发送事件,EventBus会轮流调用所有的接受类型是发送事件类型的订阅者。
说明:
1)如果事件执行过程,需要较长时间,考虑进行异步,即常见新线程进行处理。
2) 在订阅方法上,增加注解:@AllowConcurrentEvents;使得事件可以并发执行。
EventBus不会使用多线程调用处理程序方法,除非使用@AllowConcurrentEvent注释处理程序方法。通过@AllowConcurrentEvent注解注释处理方法,我们断言处理程序方法是线程安全的。使用@AllowConcurrentEvent注释的处理程序方法,本身不会在EventBus中注册。
2、代码示例
1)业务类之产品类
package com.eventBus;
/**
* Created by Liuxd on 2018-08-19.
*/
public class Car {
private String name;
private String color;
public Car(String name, String color) {
this.name = name;
this.color = color;
}
public Car() {
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getColor() {
return color;
}
public void setColor(String color) {
this.color = color;
}
}
2、业务之操作类
package com.eventBus;
/**
* Created by Liuxd on 2018-08-19.
*/
public class Factory {
public static Integer num = 0;
public void operate(Car car) {
System.out.println("当前累计num:" + num++);
System.out.println("生产新汽车,名称" + car.getName() + "颜色" + car.getColor() + " 线程ID:" + Thread.currentThread().getId());
}
}
3、事件发布类:
package com.eventBus;
import com.google.common.eventbus.EventBus;
import java.util.Random;
/**
* Created by Liuxd on 2018-08-19.
*/
public class EventProducer {
public final static String[] nameArray = new String[]{"奥迪", "大众", "奔驰", "宝马", "尼桑"};
public final static String[] colorArray = new String[]{"黑色", "白色", "红色", "银色", "黄色"};
public final static Random random = new Random();
private final static EventBus eventBus = new EventBus();
private final static EventBussListener loggerListener = new EventBussListener();
public static void main(String[] args) {
eventBus.register(loggerListener);
System.out.println("主线程ID:" + Thread.currentThread().getId());
for (int i = 0; i < 1000; i++) {
new Thread() {
@Override
public void run() {
Car car = new Car(nameArray[random.nextInt(5)], colorArray[random.nextInt(5)]);
eventBus.post(car);
}
}.start();
}
}
}
4、订阅类---监听类:
package com.eventBus;
import com.google.common.eventbus.Subscribe;
/**
* Created by Liuxd on 2018-08-19.
*/
public class EventBussListener {
public final static Factory factory = new Factory();
// @AllowConcurrentEvents请注意注释和放开的区别
@Subscribe
// @AllowConcurrentEvents
public void executeOperate(Car car) {
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
factory.operate(car);
// throw new RuntimeException("认为抛出异常");
}
}