设计模式之观察者模式(Observer)

8 篇文章 0 订阅
7 篇文章 0 订阅

1. 简介

观察者模式允许你定义一种订阅机制,可在对象事件发生时,通知多个 “观察” 该对象的其他对象

在这里插入图片描述

1.1 作用

观察者模式定义的是一种一对多的关系:

  • 一是主题类,多是观察者类
  • 当主题类的状态发生改变时,会通知与之对应的观察者类,去相应地更新状态
  • 支持动态增加、删除观察者类对象

解决的问题

  • 如下图所示,每次到货都要发邮件给各家各户
    在这里插入图片描述

  • 用观察者模式解决问题:商店浪费资源去通知没有需求的客户
    在这里插入图片描述

优缺点

✔ 优点❌ 缺点
无需修改发布者代码就能引入新的订阅者类 (如果是发布者接口则可轻松引入发布者类)订阅者的通知顺序是随机的
可以在运行时建立对象之间的联系

1.2使用场景

  • 当应用中一些对象必须观察其他对象时,可用观察者模式,但仅能在有限的复杂度或特定情况下使用
  • 当一个对象状态的改变需要改变其他对象, 或实际对象是事先未知的或动态变化的时, 可使用观察者模式

2. 实现

2.1 UML 图

在这里插入图片描述

2.2 代码

Program:

namespace Observer
{
    class Program
    {
        static void Main(string[] args)
        {
            Subject subject = new Subject();
            ObserverA observerA = new ObserverA();
            ObserverB observerB = new ObserverB();

            subject.Attach(observerA);
            subject.Attach(observerB);

            subject.SomeBusinessLogic();
            subject.SomeBusinessLogic();

            subject.Detach(observerA);

            subject.SomeBusinessLogic();
        }
    }
}

IObserver:

namespace Observer
{
    interface IObserver
    {
        public void Update(ISubject subject) { }
    }
}

ObserverA:

using System;

namespace Observer
{
    class ObserverA: IObserver
    {
        public void Update(ISubject subject)
        {
            if ((subject as Subject).state > 2)
            {
                Console.WriteLine("ObserverAAA Update ... state: " + (subject as Subject).state.ToString());
            }
        }
    }
}

ObserverB:

using System;

namespace Observer
{
    class ObserverB:IObserver
    {
        public void Update(ISubject subject)
        {
            if((subject as Subject).state > 0 && (subject as Subject).state < 3)
            {
                Console.WriteLine("ObserverBBB Update ... state: " + (subject as Subject).state.ToString());
            }
        }
    }
}

ISubject:

namespace Observer
{
    interface ISubject
    {
        public void Attach(IObserver observer) { }
        public void Detach(IObserver observer) { }
        public void Notify() { }
    }
}

Subject:


using System;
using System.Collections.Generic;
using System.Threading;

namespace Observer
{
    class Subject: ISubject
    {
        public int state;
        private List<IObserver> observerList = new List<IObserver>();

        public void Attach(IObserver observer) 
        {
            if (observer != null)
            {
                observerList.Add(observer);
            }
        }

        public void Detach(IObserver observer) 
        {
            if (observer != null)
            {
                observerList.Remove(observer);
            }
        }

        public void Notify()
        {
            foreach (var observer in observerList)
            {
                observer.Update(this);
            }
        }

        public void SomeBusinessLogic()
        {
            Console.WriteLine("Subject do SomeBusinessLogic");
            state = new Random().Next(0, 10);

            Thread.Sleep(15);
            Console.WriteLine("Subject SomeBusinessLogic state: " + state.ToString());

            Notify();
        }
    }
}

F5 运行结果:

Subject do SomeBusinessLogic
Subject SomeBusinessLogic state: 8
ObserverAAA Update … state: 8
Subject do SomeBusinessLogic
Subject SomeBusinessLogic state: 0
Subject do SomeBusinessLogic
Subject SomeBusinessLogic state: 1
ObserverBBB Update … state: 1

参考:观察者模式

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值