使用EventBus对模块解耦(附实例)
用于模块间解耦,通过发布订阅的方式调用,每个人只负责自己的那部分。
写个小例子,比如现在有三个模块,订单、购物车、优惠券,由不同的人负责开发。
负责订单模块的人现在需要写个生成订单的方法,生成订单的逻辑包括删除购物车项、标记优惠券已使用。
如果直接调用购物车、优惠券两个模块中的方法,耦合性高。
此时可以使用EventBus进行解耦。
public class EventBus
{
private EventBus() { }
private static Object syncObj = new object();
private static EventBus _instance = null;
public static EventBus Instance
{
get
{
if (_instance == null)
{
lock (syncObj)
{
if (_instance == null)
{
_instance = new EventBus();
}
}
}
return _instance;
}
}
private ConcurrentDictionary<string, List<Action<object[]>>> _dict = new ConcurrentDictionary<string, List<Action<object[]>>>();
private bool ExistEvent(string eventName)
{
if (_dict.ContainsKey(eventName))
{
return true;
}
return false;
}
public void InvokeEvent(string eventName,object[] args)
{
if (!this.ExistEvent(eventName))
{
return;
}
foreach (var eventHandler in this._dict[eventName])
{
eventHandler.Invoke(args);
}
}
public void AddEvent(string eventName, Action<object[]> eventHandler)
{
if (this.ExistEvent(eventName))
{
this._dict[eventName].Add(eventHandler);
}
else {
this._dict[eventName] = new List<Action<object[]>> { eventHandler };
}
}
public void AddEvent(string eventName, List<Action<object[]>> eventHandlerList)
{
if (this.ExistEvent(eventName))
{
this._dict[eventName].AddRange(eventHandlerList);
}
else
{
this._dict[eventName] = eventHandlerList;
}
}
public void RemoveEvent(string eventName)
{
if (this.ExistEvent(eventName))
{
this._dict.TryRemove(eventName,out var value);
}
}
public void RemoveEvent(string eventName, Action<object[]> eventHandler)
{
if (this.ExistEvent(eventName))
{
this._dict[eventName].Remove(eventHandler);
}
}
}
public class ShopCartService
{
/// <summary>
/// 删除购物车
/// </summary>
/// <param name="shopCartID"></param>
public void RemoveShopCart(int orderID)
{
Console.WriteLine($"已删除订单{orderID}的购物车项");
}
}
public class CouponService
{
/// <summary>
/// 标记优惠券已使用
/// </summary>
public void RecordUsedCoupon(int orderID)
{
Console.WriteLine($"已将订单{orderID}标记已使用优惠券");
}
}
public class OrderService
{
/// <summary>
/// 创建订单
/// </summary>
public void CreateOrder()
{
;
Console.WriteLine($"生成订单");
EventBus.Instance.InvokeEvent(EventNames.CREATEORDER_EVENT, new object[] { orderID });
}
}
public static class EventNames
{
public static string CREATEORDER_EVENT = "CreateOrder";
}
---------------------------------------------------------------------------
订阅、发布
static void Main(string[] args)
{
//订阅
EventBus.Instance.AddEvent(EventNames.CREATEORDER_EVENT, new List<Action<object[]>>
{
(args)=>{ ].ToString())); },
(args)=>{ ].ToString())); }
});
var orderService = new OrderService();
orderService.CreateOrder();
}
使用EventBus对模块解耦(附实例)的更多相关文章
- Java经典设计模式之十一种行为型模式(附实例和详解)
Java经典设计模式共有21中,分为三大类:创建型模式(5种).结构型模式(7种)和行为型模式(11种). 本文主要讲行为型模式,创建型模式和结构型模式可以看博主的另外两篇文章:Java经典设计模式之 ...
- Java设计模式之十一种行为型模式(附实例和详解)
Java经典设计模式共有21中,分为三大类:创建型模式(5种).结构型模式(7种)和行为型模式(11种). 本文主要讲行为型模式,创建型模式和结构型模式可以看博主的另外两篇文章:J设计模式之五大创建型 ...
- (转)Java经典设计模式(3):十一种行为型模式(附实例和详解)
原文出处: 小宝鸽 Java经典设计模式共有21中,分为三大类:创建型模式(5种).结构型模式(7种)和行为型模式(11种). 本文主要讲行为型模式,创建型模式和结构型模式可以看博主的另外两篇文章:J ...
- Linux chmod命令修改文件与文件夹权限的命令附实例
Linux chmod命令修改文件与文件夹权限的命令附实例 作者:佚名 字体:[增加 减小] 来源:互联网 时间:05-01 20:46:07我要评论 在linux中要修改一个文件夹或文件的权限我们需 ...
- Java经典设计模式之七大结构型模式(附实例和详解)
博主在大三的时候有上过设计模式这一门课,但是当时很多都基本没有听懂,重点是也没有细听,因为觉得没什么卵用,硬是要搞那么复杂干嘛.因此设计模式建议工作半年以上的猿友阅读起来才会理解的比较深刻.当然,你没 ...
- Java设计模式之七大结构型模式(附实例和详解)
博主在大三的时候有上过设计模式这一门课,但是当时很多都基本没有听懂,重点是也没有细听,因为觉得没什么卵用,硬是要搞那么复杂干嘛.因此设计模式建议工作半年以上的猿友阅读起来才会理解的比较深刻.当然,你没 ...
- (转)Java经典设计模式(2):七大结构型模式(附实例和详解)
原文出处: 小宝鸽 总体来说设计模式分为三大类:创建型模式.结构型模式和行为型模式. 博主的上一篇文章已经提到过创建型模式,此外该文章还有设计模式概况和设计模式的六大原则.设计模式的六大原则是设计模式 ...
- web自动化测试-模块驱动测试实例和数据驱动测试实例
一.模块驱动测试实例 把登录和退出统一封装在login类中,若把login类单独放在一个文件中,就可以给任一测试脚本调用,这里就跟测试脚本放一起 from selenium import webdri ...
- Python命令行参数解析模块getopt使用实例
Python命令行参数解析模块getopt使用实例 这篇文章主要介绍了Python命令行参数解析模块getopt使用实例,本文讲解了使用语法格式.短选项参数实例.长选项参数实例等内容,需要的朋友可以参 ...
随机推荐
- snowflake ID生成器
背景 Snowflake 是 Twitter 内部的一个 ID 生算法, 可以通过一些简单的规则保证在大规模分布式情况下生成唯一的 ID 号码. 其组成为: 第一个 bit 为未使用的符号位. 第二部 ...
- find命令常用参数
目录 -name -type -size -empty -inum -links -perm -user -group -atime -ctime -mtime -amin -cmin -mmin - ...
- mysql备份、还原数据库(命令行)
这里记录下MySQL如何通过命令行备份和还原数据库. 简单的三个步骤 方法很简单,可以分为三个步骤: 1.打开cmd控制台(命令行). 2.输入相应命令完成备份还原操作. 3.关闭cmd控制台. 就和 ...
- 代码语法高亮踩坑-原理,问题, PRE元素及htmlentity
语法高亮库基础原理 在研究使用能够在web页面上代码语法高显的解决方案时,发现有很多现成的开源库.比较中意的有prism.js,highlightjs.他们的原理基本上核心就两点: 1. 利用html ...
- Windows下分布式环境搭建以及简单测试
环境配置: 解压文件: Nginx服务器和Tomcat服务器 Tomcat服务器配置:(conf/server.xml) Nginx配置:(conf/nginx.conf) 安装memcached H ...
- nginx配置ssl证书实现https
一,环境说明 服务器系统:centos6 服务器IP地址:0.0.0.0 域名:bjubi.com 二,域名解析到服务器 在阿里云控制台-产品与服务-云解析DNS-找到需要解析的域名点“解析”,进入解 ...
- 349套HTML5+CSS3各行各业网站模板免费下载
场景 349套HTML5+CSS3各行各业网站模板. Web前端开发是从网页制作演变而来的,名称上有很明显的时代特征.在互联网的演化进程中,网页制作是Web1.0时代产物,那时网站的主要内容是静态的, ...
- div等高布局
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title> ...
- Java 之 Set 源码分析
一.HashSet 构造方法: HashSet() :构造一个新的空 set,其底层 HashMap 实例的默认初始容量是 16,加载因子是 0.75 源码: 二.LinkedHashSet 构造方 ...
- Unity3D协程(转)
这篇文章转自:http://blog.csdn.net/huang9012/article/details/38492937 协程介绍 在Unity中,协程(Coroutines)的形式是我最喜欢的功 ...