C#之观察者

Iron之观察者

引言

上一篇说的职责链模式,很有意思的一个模式,今天这个模式也是很有意思的一个模式,还是不啰嗦了直接进入主题吧。

场景介绍:在上一遍中说到用到部件检测,很巧妙的让调用者和处理者解耦了(没有看过上篇的文章也没关系,只是剧情是要接着发展的),要把部件拿去检测是要让个人来盯着看呢?还是部件生产好了自动就被拿去检测了呢?毋庸置疑必须是自动化的。

看一下部件的结构


 1     /// <summary>
2 /// 部件
3 /// </summary>
4 public class ComponentModel
5 {
6 public string Name { get; set; }
7 public int Value
8 {
9 get
10 {
11 return 5;
12 }
13 }
14
15 }

这个部件还是上一篇的部件,没有做任何改动。只是示例,为了让没看过上一篇的朋友知道。

按照场景里所要求的,定义了下面的两个类型,ComponentModelFactory类型,ComponentModel类型工厂负责生产ComponentModel部件,并且在完成时通知要另外处理部件的对象。
ExecutionCheck类型,就是要要被通知到的对象,它等待着别人告诉它
“有部件生产好了,需要被你送去检测”,不会它会很无聊。


 1    /// <summary>
2 /// 示例ComponentModel类型工厂 生产了ComponentModel 通知ExecutionCheck对象去检测
3 /// </summary>
4 public class ComponentModelFactory
5 {
6 public static ComponentModel ComModelFactory()
7 {
8 return new ComponentModel();
9 }
10 }
11 /// <summary>
12 /// 送ComponentModel对象去检测
13 /// </summary>
14 public class ExecutionCheck
15 {
16 public void ComponentModelCheck(ComponentModel comModel)
17 {
18 //送去执行检测
19 //或者是一些其他操作
20 }
21 }

来看看调用代码:


1 ExecutionCheck executionCheck = new ExecutionCheck();
2 executionCheck.ComponentModelCheck(ComponentModelFactory.ComModelFactory());
3 executionCheck.ComponentModelCheck(ComponentModelFactory.ComModelFactory());
4 executionCheck.ComponentModelCheck(ComponentModelFactory.ComModelFactory());

似乎是解决了问题,但是结果糟透了,虽然executionCheck很高兴,因为它有活干了,我只能以这样的方式去通知executionCheck,或许有人说修改下ComponentModelFactory类型会好一点,我知道是这样的:


 1     public class ComponentModelFactory
2 {
3 public static ComponentModel ComModelFactory()
4 {
5 return new ComponentModel();
6 }
7 public void PastMessage(ComponentModel componentModel,ExecutionCheck executionCheck)
8 {
9 executionCheck.ComponentModelCheck(componentModel);
10 }
11 }

调用代码则调整为:


1 ComponentModelFactory componentModelFactory = new ComponentModelFactory();
2 ExecutionCheck executionCheck=new ExecutionCheck();
3 componentModelFactory.PastMessage(ComponentModelFactory.ComModelFactory(), executionCheck);

这样的结果,调用方式没问题了,可是ComponentModelFactory类型的内部居然有着这样高的耦合,无法忍受,必须得找出一种方式或者模式来解决这样的难题,不然寝食难安!!!!

定义对象间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并被自动更新。
                                                                                      

                                                                                                                                      
——Gof

按照模式的定义重新来过(会有点不一样的地方中心思想不变),先对ExecutionCheck 类型进行抽象


 1     /// <summary>
2 /// 抽象的ExecutionCheck(抽象观察者)
3 /// </summary>
4 public abstract class ABSExecutionCheck
5 {
6 public abstract void ComponentModelCheck(ComponentModel comModel);
7 }
8
9 /// <summary>
10 /// 送ComponentModel对象去检测(观察者)
11 /// </summary>
12 public class ExecutionCheck:ABSExecutionCheck
13 {
14 public override void ComponentModelCheck(ComponentModel comModel)
15 {
16 //送去执行检测
17 //或者是一些其他操作
18 }
19 }

然后再对ComponentModelFactory进行改造,并且抽象它。


 1     /// <summary>
2 /// 抽象目标
3 /// </summary>
4 public abstract class ABSComponentModelFactory
5 {
6 protected ABSExecutionCheck absExecutionCheck;
7 public abstract void RegisterABSExecutionCheck(ABSExecutionCheck executionCheck);
8 public abstract void ClearABSExecutionCheck();
9 public abstract void PastMessage(ComponentModel componentModel);
10 }

ABSComponentModelFactory类型是要让ComponentModelFactory类型实现的,从这里可以看出是遵循设计原则的面对抽象编程的,当然了最后一个PastMessage函数忽略掉,现在来看一下实现了抽象目标ABSComponentModelFactory的ComponentModelFactory(具体目标)的实现。


 1     /// <summary>
2 /// 示例ComponentModel类型工厂 生产了ComponentModel 通知ExecutionCheck对象去检测 (具体目标)
3 /// </summary>
4 public class ComponentModelFactory:ABSComponentModelFactory
5 {
6 public static ComponentModel ComModelFactory()
7 {
8 return new ComponentModel();
9 }
10
11 public override void RegisterABSExecutionCheck(ABSExecutionCheck executionCheck)
12 {
13 absExecutionCheck = executionCheck;
14 }
15
16 public override void ClearABSExecutionCheck()
17 {
18 absExecutionCheck = null;
19 }
20 public override void PastMessage(ComponentModel componentModel)
21 {
22 absExecutionCheck.ComponentModelCheck(componentModel);
23 }
24 }

现在再来看一下调用的代码:


1 ABSExecutionCheck executionCheck = new ExecutionCheck();
2 ABSComponentModelFactory componentModelFactory = new ComponentModelFactory();
3 componentModelFactory.RegisterABSExecutionCheck(executionCheck);
4 componentModelFactory.PastMessage(ComponentModelFactory.ComModelFactory());

这样就比较稳固了,在第一行new ExecutionCheck()的地方可以动态注入,和最后行的工厂生产对象一样。因为这里只是示例就不会很严谨。
还有要说的就是定义中是一对多,这样可以修改ABSComponentModelFactory类型中的字段,修改为集合类型就可以了。
把对应的实现类也适当的修改一下就可以了。

观察者就讲到这里。下一篇是外观,敬请期待。

作者:金源

出处:http://www.cnblogs.com/jin-yuan/

本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面

时间: 2024-08-29 20:31:24

C#之观察者的相关文章

Ember.js 入门指南——观察者(observer)

本系列文章全部从(http://ibeginner.sinaapp.com/)迁移过来,欢迎访问原网站. 1,观察者使用 Ember可以察觉所有属性的变化,包括计算属性.观察者是非常有用的,特别是计算属性绑定之后需要同步的时候. 观察者经常被Ember开发过度使用.Ember框架本身已经大量使用观察者,但是对于大多数的开发者面对开发问题时使用计算属性是更适合的解决方案. 使用方式:可以用"Ember.observer"设置一个对象为观察者. // Observer对于Emberjs来说

属性观察者(监听属性的变化)

// 属性观察者, 用于监听属性变化, 在属性变化的时候调用 class Person { var name: String = "" { // 也可以写成willSet{}, 系统默认会传入一个名为newValue的参数 willSet(newValue) { print("name这个属性将被修改了, \(newValue)") } // 也可以写成didSet{} didSet(newValue) { print("name这个属性已经被修改了, \

理解设计模式(观察者)

观察者模式,保证主题和若干观察者之间的一致性. 概述 有时又被称为发布-订阅Subscribe>模式.模型-视图View>模式.源-收听者Listener>模式或从属者模式 此种模式通常被用来实现事件处理系统 特定环境 一个对象改变,同时引发其他若干对象发生变化时 主动改变的对象和被动变化的对象之间相对独立,以便复用和维护 一类问题 一个系统,由一个对象和若干协作对象组成,同时要避免这些对象之间相互耦合 解决方案 抽象主题角色 具体主题角色 抽象观察者角色 具体观察者角色 抽象主题角色

Observer(观察者)模式

1.概述 一些面向对象的编程方式,提供了一种构建对象间复杂网络互连的能力.当对象们连接在一起时,它们就可以相互提供服务和信息. 通常来说,当某个对象的状态发生改变时,你仍然需要对象之间能互相通信.但是出于各种原因,你也许并不愿意因为代码环境的改变而对代码做大的修改.也许,你只想根据你的具体应用环境而改进通信代码.或者,你只想简单的重新构造通信代码来避免类和类之间的相互依赖与相互从属. 2.问题 当一个对象的状态发生改变时,你如何通知其他对象?是否需要一个动态方案――一个就像允许脚本的执行一样,允

设计模式——观察者

观察者模式定义了对象之间的一对多依赖,当一个对象改变状态时,他的所有的依赖者都会收到通知并自动更新: 定义主题,主题的功能是持有观察者的引用,提供注册.取消注册和通知,并且有状态:观察者实现接口中的update方法,必须注册具体主题: JDK自带了对观察者的支持功能 被观察者Observable对象,提供add/delete/notifyObserver()和setChanged()设置状态方法 观察者Observer接口,提供update()方法进行相关的更新操作. 观察者类图: 以下程序模拟

Cocos中的观察者设计模式与通知机制

观察者(Observer)模式也叫发布/订阅(Publish/Subscribe)模式,是 MVC( 模型-视图-控制器)模式的重要组成部分.天气一直是英国人喜欢讨论的话题,而最近几年天气的变化也成为中国人非常关注的话题.我会根据天气预报决定是坐地铁还是开车上班,我的女儿也会根据天气预报决定明天穿哪件衣服.于是我在移动公司为我的手机定制了天气预报短信通知服务,它的工作模型如图所示. 每天气象局将天气预报信息投送给移动运营商,移动运营商的短信中心负责把天气预报发送给定制过这项服务的手机.在软件系统

观察者模式分析、结构图及基本代码

 定义:观测者模式定义了一种一对多的依赖关系,让多个观测者对象同时监听某一个主题对象.这个主题对象在状态发生变化时,会通知所有观测者对象,使它们能够自动更新自己. 结构图: Subject类,可翻译为主题或抽象通知者,一般用一个抽象类或者一个接口实现.它把所有对观察者对象的引用保存在一个聚集里,每个主题都可以有任何数量的观察者.抽象主题提供一个接口,可以增加和删除观测者. Observe类,抽象观测者,为所有的具体观察者定义一个接口,在得到主题的通知时更新自己.这个接口叫更新接口.抽象观察者

观察者设计模式

/** * 事件接口即被观察者 * * @author Host * */ publicinterface Event { void attach(Listener listener); void detach(Listener listener); void notifyListener(); } /** * 事件监听者观察者 * * @author Host * */ publicinterface Listener { void execute(); } 事件源的一个实现类(磁盘事件) p

内容观察者

在Android项目中我们常常需要检测另一个应用私有数据的变化与否,如何检测另一个数据库应用中的数据变化,我们通过下面的案例来讲述具体的操作. 应用场景:有两个应用,一个是"01_数据库应用",另一个是"07_内容观察者":第二个应用监测第一个应用数据库的变化,当第一个应用数据库发生变化便即时通知第二个应用.实现方法如下: 轮询 若要监测数据库中数据的变化与否,我们可以在当前应用中编写一个定时器,该定时器的工作是每隔一段时间查询数据库中的数据,将查询的结果与之前查询

内容观察者使用(程序锁应用中的使用)

1.在Dao层的增删改查方法中,添加一句代码,通知内容观察者,数据库发生改变. context.getContentResolver().notifyChange(Uri.parse("content://applock/change"), null); 参数1:自定义Uri,在注册内容观察者时匹配 2.在需要使用内容观察者的类中(即DogService),注册内容观察者.一旦数据库的数据发生改变,就要调用内容观察者中的onchange方法,在这里就是再一次findAll(). //使