观察者模式 C#版

观察者模式(Observer):在对象间定义一种一对多的依赖关系,以便当某对象的状态改变时,与它存在依赖关系的所有对象都能收到通知并自动进行更新。

  • MVC模式的底层可以说就是利用了观察者模式

基础设计

我们可以使用如下的方式设计一个简单的观察者模式,在被观察者中需要存储一个观察者组,提供一个发送消息的方法对观察组进行消息推送。

在观察者中提供一个消息响应的方法,响应消息。

	/// <summary>
    /// 事件
    /// </summary>
    public enum Event
    {
        捡到金币,
        通关
    }
 	/// <summary>
    /// 观察者接口
    /// </summary>
    public interface IObserver
    {
        /// <summary>
        /// 接收通知
        /// </summary>
        /// <param name="subject"></param>
        /// <param name="eventMsg"></param>
        void OnNotify(Subject subject, Event eventMsg);
    }

    /// <summary>
    /// 被观察者接口
    /// </summary>
    public interface ISubject
    {
        List<IObserver> Observers();
        void AddObserver(IObserver observer);
        void RemoveObserver(IObserver observer);
    }
	 /// <summary>
    /// 观察者
    /// </summary>
    public class Observer : IObserver
    {
        public void OnNotify(Subject subject, Event eventMsg)
        {
            switch (eventMsg)
            {
                case Event.捡到金币:
                    subject.Score += 10;
                    break;
                case Event.通关:
                    subject.Score += 100;
                    break;
            }
        }
    }

    /// <summary>
    /// 被观察者
    /// </summary>
    public class Subject : ISubject
    {
        public int Score;
        private readonly List<IObserver> _observers;
		
        /// <summary>
        /// 发送消息
        /// </summary>
        /// <param name="eventMsg"></param>
        public void Notify(Event eventMsg)
        {
            _observers.ForEach(x=>x.OnNotify(this,eventMsg));
        }
        
        public Subject()
        {
            _observers = new List<IObserver>();
        }

        public List<IObserver> Observers()
        {
            return _observers;
        }

        public void AddObserver(IObserver observer)
        {
            _observers.Add(observer);
        }

        public void RemoveObserver(IObserver observer)
        {
            _observers.Remove(observer);
        }
    }

使用委托和事件

在Csharp中内置了委托和事件来处理这种一对多的响应方式。

using System;

namespace ObserverPattern
{
    /// <summary>
    /// 观察者模式
    /// </summary>
    internal static class Program
    {
        
        public static void Main(string[] args)
        {
            var c = new Cat() {Name = "小白"};
            var m = new Mouse(c) {Name = "小鼠"};
            c.OnCatCom();

        }
    }

    class Cat
    {
        public string Name { get; set; }
        public event Action catCom;
        public virtual void OnCatCom()
        {
            Console.WriteLine("{0}来了",Name);
            catCom?.Invoke();
        }
    }

    class Mouse
    {
        public string Name { get; set; }
        public Mouse(Cat cat)
        {
            //将事件绑定到方法
            cat.catCom += this.MouseRun;
        }
        private void MouseRun()
        {
            Console.WriteLine("{0}快跑!!",Name);
        }        
    }
}

思考

其实观察者模式就是对象的一种间接同步调用,使用这种方法是为了解除耦合,达到统一分配管理的作用。

从上文提到的可以知道,这种模式是同步的,也就是说当存在一组观察者时,那么可能会导致阻塞,但在实际中可能没这么严重,但在使用中我们还需注意。

如果你在每次响应后给出一个状态,表示通知的响应情况,那么这就接近 责任链模式了。

销毁对象?

在书中提到一个问题很有趣,在观察者模式中销毁对象该怎么办呢?

在销毁对象前,需要解除监听,确保对象被正确销毁。

现状

观察者模式出现于1994年(比我还大😄),因此基本都是基于类来实现的,但现在更流行函数式编程,可能不太符合现在的编程美学。例如C#的event就是现代化的观察者模式。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值