zoukankan      html  css  js  c++  java
  • 设计模式之二——从江湖情报变动通知各门派看观察者模式

    我们看武侠小说的时候,有这么一个情节,就是武侠世界中总有一个神秘组织,对江湖的情报进行搜集,然后把情报进行分析整理,向江湖主要门派进行通报。将问题用更精确点的语言描述一遍,就是有一个情报组织,他们组织里有一些人在监视江湖上的各种事件,然后汇总到情报组织中,情报组织将所有情报进行汇总分析,有大的事件发生的时候他们把情报进行更新,更新的信息包括BigEvent武林大事件、WugongRank武功排行榜、WeaponRank武器排行榜等,然后将信息发放到Shaolin少林、Wudang武当、Emei峨眉等一些大门派。

     

    2 问题分析

    这个业务关系和报纸出版的方式很类似,就是主办者+订阅者的方式,情报组织负责提供数据,各大门派开始订阅,如果信息变动则给订阅的门派提供信息,门派可以看作是观察者,可以注册,接收情报信息,也可以注销,不再接收信息。

    情报数据和门派之间存在一对多的依赖,当情报数据发生改变时,所有的门派都会收到通知并自动更新数据。再用更通用的语言描述一次,定义了对象之间的一对多依赖,当一个对象改变状态时,它的所有依赖者都会收到通知并自动更新。我们将情报数据抽象为subject主题,将各门派抽象为observer观察者,得到观察者模式的类图。

     

    主题和观察者相对独立,它们之间并不会相互影响,只要遵循接口关系设计,它们就可以被自由的改变。这也是一个软件设计原则,尽量减少对象之间的耦合。松耦合的设计之所以能让我们建立有弹性的软件系统,就是因为松耦合能够应对变化,对象之间的依赖关系被降低了。

    3 设计情报通知系统

    根据观察者模式类图,我们进行江湖情报通知的详细设计,其中情报数据类实现主题接口,除了有注册观察者,移除观察者,通知观察者等方法外,还有获取情报的方法以及情报改变的方法,情报改变的方法用于在情报改变的时候,更新情报信息,然后执行通知观察者方法。

    增加InformationDisplay信息展示接口,接口只提供一个display展示方法,用来展示各种数据。观察者的具体实现类既实现观察者接口,也实现信息展示接口。

     

    4 代码实现

    根据上面的设计图,进行代码编程实现。

    4.1 三个接口代码

    public interface Subject {
        public void registerObserver(Observer o);
        public void removeObserver(Observer o);
        public void notifyObserver();
    }

    public interface Observer {
        public void update(String bigEvent,String wugongRank,String weaponRank);
    }
    public interface InformationDisplay {
        public void display();
    }

    4.2 具体主题的实现类(情报数据类)

    public class InformationData implements Subject {
        private ArrayList observers;//用来记录观察者
        private String bigEvent;
        private String wugongRank;
        private String weaponRank;

        public InformationData(){
            observers = new ArrayList();
        }

        public void registerObserver(Observer o){
            observers.add(o);
        }

        public void removeObserver(Observer o){
            int i = observers.indexOf(o);
            if (i >= 0){
                observers.remove(o);
            }
        }

        public void notifyObserver(){
            for (int i = 0;i < observers.size();i++){
                Observer observer = (Observer) observers.get(i);
                observer.update(bigEvent,wugongRank,weaponRank);
            }
        }

        public void informationChanged(){
            notifyObserver();
        }

        public void setInformation(String bigEvent,String wugongRank,String weaponRank){
            this.bigEvent = bigEvent;
            this.wugongRank = wugongRank;
            this.weaponRank = weaponRank;
            informationChanged();
        }
    }

    4.3 具体观察者实现类(武林大事件展示类)

    具体观察者实现类有三个,武林大事件展示类、武功排名展示类和武器排名展示类,三个类比较相似,此处只以武林大事件展示类为例,进行代码展示。

    public class BigEventDisplay implements Observer,InformationDisplay {

        private String bigEvent;
        private Subject informationData;

        public BigEventDisplay(Subject informationData){
            this.informationData = informationData;
            informationData.registerObserver(this);
        }

        @Override
        public void update(String bigEvent, String wugongRank, String weaponRank) {
            this.bigEvent = bigEvent;
            display();
        }

        @Override
        public void display() {
            System.out.println("当前发生的武林大事有:"+bigEvent);
        }
    }

    4.4 测试类及结果

    public class InformationNotify {
        public static void main(String[] args) {
            InformationData informationData = new InformationData();

            BigEventDisplay bigEventDisplay = new BigEventDisplay(informationData);

            informationData.setInformation("五大派正在围攻光明顶,张无忌力战各大掌门。","张无忌排名第一","小李飞刀排名第一");
        }
    }

    "C:Program FilesJavajdk1.8.0_111injava.exe" -

    当前发生的武林大事有:五大派正在围攻光明顶,张无忌力战各大掌门。

    Process finished with exit code 0

    5 结语

    观察者模式在JDK中也有实现,Java API内置的观察者模式,在java.util包内,其中Observable类对应我们的Subject接口,Observer接口对应我们的Observer接口,观察者模式的思想是一致的,使用上也比较类似,不过,JDK为我们做好的封装,使用起来更加方便。

  • 相关阅读:
    Linux 学习手记(4):Linux系统常用Shell命令
    Linux 学习手记(3):Linux基本的文件管理操作
    Nginx的启动、停止与重启
    20个常用正则表达式
    MongoDB增删改查实例
    MongoDB 查询总结
    MongoDB数据库未授权访问漏洞及加固
    MongoDB安装
    java模拟post方式提交表单实现图片上传【转】
    Java图片处理 Thumbnails框架
  • 原文地址:https://www.cnblogs.com/coodream2009/p/10657919.html
Copyright © 2011-2022 走看看