美文网首页产品
01.观察者模式

01.观察者模式

作者: 一直流浪 | 来源:发表于2023-02-03 16:09 被阅读0次

01.观察者模式

1、认识观察者模式:

我们看看报纸和杂志的订阅是怎么回事:

(1)报社的业务就是出版报纸。

(2)向某家报社订阅报纸,只要他们有新报纸出版,就会给你送来。只要你是他们的订户,你就会一直收到新报纸。

(3) 当你不想再看报纸的时候,取消订阅,他们就不会再送新报纸来。

(4)只要报社还在运营,就会一直有人(或单位)向他们订阅报纸或者取消订阅报纸。

2、定义:

观察者模式定义了对象之间的一对多依赖,这样一来,当一个对象改变状态时,它的所有依赖者都会收到通知并自动更新。

主题和观察者定义了一对多的关系。观察者依赖于此主题,只要主题状态一有变化,观察者就会被通知。根据通知的风格,观察者可能因此新值而更新。

实现观察者模式的方法不止一种,包含 Subject 和 Observer 接口的类最为常见。

C8CE0C4C-F581-445E-B2F4-_1_105_c.jpeg

3、设计原则:

为了交互对象之间的松耦合设计而努力。

松耦合的设计之所以能让我们建立有弹性的OO系统,能够应对变化,是因为对象之间的互相依赖降到最低。

因为任何时候我们都可以添加新的观察者,因为主题唯一依赖的东西是一个实现Observer接口的对象列表。

4、举例(气象站项目):

4.1 需求:

(1)该气象站必须建立在专利申请的 WeatherData 对象上,由 WeatherData 对象负责追踪目前的天气状况(温度、湿度、气压)。

(2)建立一个应用,有三种布告板(后面可能会有更多),分别显示目前的状态、气象统计和简单的预报(三种不同形式的展示)。当WeatherData 改变时,三种布告板必须实时更新。

4.2 设计:

008068C1-4A49-44AE-A02FFFCBDB_1_201_a.jpeg

4.3 代码实现:

(1)观察者接口

/**
 * 观察者接口
 *
 * 所有观察者都要实现此接口
 */
public interface Observer {
    /**
     * 当气象观察值改变时,主题会把这些状态值传给观察者
     * @param temp
     * @param humidity
     * @param pressure
     */
    public void update(float temp, float humidity, float pressure);
}

(2)主题接口

/**
 * 主题接口
 *
 * 所有主题都要实现此接口
 */
public interface Subject {
    /**
     * 观察者注册接口
     * @param o
     */
    public void registerObserver(Observer o);

    /**
     * 观察者删除接口
     * @param o
     */
    public void removeObserver(Observer o);

    /**
     * 当主题状态改变时,通过这个方法告知所有的观察者
     */
    public void notifyObservers();

}

(3)布告板接口

/**
 * 布告板接口
 *
 * 所有布告板要实现此接口
 */
public interface DisplatElement {
    /**
     * 当布告板需要显示时,调用此方法
     */
    public void display();
}

(4)主题实现类 - 天气数据

/**
 * 天气数据
 * 
 * 主题实现类
 */
public class WeatherData implements Subject {
    /**
     * 记录所有观察者
     */
    private ArrayList observers;
    /**
     * 温度
     */
    private float temperature;
    /**
     * 湿度
     */
    private float humidity;
    /**
     * 气压
     */
    private float pressure;

    public WeatherData(ArrayList observers) {
        this.observers = observers;
    }

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

    @Override
    public void removeObserver(Observer o) {
        observers.remove(o);
    }

    @Override
    public void notifyObservers() {
        for (int i = 0; i < observers.size(); i++) {
            Observer observer = (Observer) observers.get(i);
            observer.update(temperature, humidity, pressure);
        }
    }

    /**
     * 当检测到观察值发生改变,并且达到要通知的条件时,通知所有观察者
     */
    public void measurementsChanged(){
        //TODO 检测是否达到通知条件,比如必须是温度等条件达到0.5的浮动再通知观察者

        notifyObservers();
    }

    /**
     * 当传感器返回测量的数据,会调用此方法
     * @param temperature
     * @param humidity
     * @param pressure
     */
    public void setMeasurements(float temperature,float humidity,float pressure){
        this.temperature = temperature;
        this.humidity = humidity;
        this.pressure = pressure;
        measurementsChanged();
    }

}

(5)三个布告板实现类,只有现实的属性不同。

public class CurrentConditionsDisplay implements Observer, DisplatElement {
    /**
     * 温度
     */
    private float temperature;
    /**
     * 湿度
     */
    private float humidity;

    /**
     * 主题
     */
    private Subject weatherData;

    public CurrentConditionsDisplay(Subject weatherData) {
        this.weatherData = weatherData;
        weatherData.registerObserver(this);
    }

    @Override
    public void display() {
        System.out.println("CurrentConditionsDisplay【temperature:" +  temperature + ";humidity:" + humidity+"】");
    }

    @Override
    public void update(float temp, float humidity, float pressure) {
        this.temperature = temp;
        this.humidity = humidity;
        display();
    }
}
public class ForecastDisplay implements Observer, DisplatElement {
    /**
     * 湿度
     */
    private float humidity;
    /**
     * 气压
     */
    private float pressure;

    /**
     * 主题
     */
    private Subject weatherData;

    public ForecastDisplay(Subject weatherData) {
        this.weatherData = weatherData;
        weatherData.registerObserver(this);
    }

    @Override
    public void display() {
        System.out.println("ForecastDisplay【humidity:" +  humidity + ";pressure:" + pressure+"】");
    }

    @Override
    public void update(float temp, float humidity, float pressure) {
        this.pressure = pressure;
        this.humidity = humidity;
        display();
    }
}
public class StatisticsDisplay implements Observer, DisplatElement {
    /**
     * 温度
     */
    private float temperature;

    /**
     * 气压
     */
    private float pressure;

    /**
     * 主题
     */
    private Subject weatherData;

    public StatisticsDisplay(Subject weatherData) {
        this.weatherData = weatherData;
        weatherData.registerObserver(this);
    }

    @Override
    public void display() {
        System.out.println("StatisticsDisplay【temperature:" +  temperature + ";pressure:" + pressure+"】");
    }

    @Override
    public void update(float temp, float humidity, float pressure) {
        this.temperature = temp;
        this.pressure = pressure;
        display();
    }
}

(6)测试类

public class WeatherStation {
    public static void main(String[] args) {
        WeatherData weatherData = new WeatherData(new ArrayList<Observer>());

        CurrentConditionsDisplay currentConditionsDisplay = new CurrentConditionsDisplay(weatherData);
        ForecastDisplay forecastDisplay = new ForecastDisplay(weatherData);
        StatisticsDisplay statisticsDisplay = new StatisticsDisplay(weatherData);

        weatherData.setMeasurements(50,60,30f);
        weatherData.setMeasurements(40,50,20f);
        weatherData.setMeasurements(60,20,40f);
    }
}
0308F50D-DD12-4D3C-8FD3-BBFCFD9A7962_1_201_a.jpeg

相关文章

  • 01.观察者模式

    01.观察者模式 1、认识观察者模式: 我们看看报纸和杂志的订阅是怎么回事: (1)报社的业务就是出版报纸。 (2...

  • 11.9设计模式-观察者模式-详解

    设计模式-观察者模式 观察者模式详解 观察者模式在android中的实际运用 1.观察者模式详解 2.观察者模式在...

  • RxJava基础—观察者模式

    设计模式-观察者模式 观察者模式:观察者模式(有时又被称为发布(publish )-订阅(Subscribe)模式...

  • 前端面试考点之手写系列

    1、观察者模式 观察者模式(基于发布订阅模式) 有观察者,也有被观察者。 观察者需要放到被观察者列表中,被观察者的...

  • RxJava 原理篇

    一、框架思想 观察者模式观察者自下而上注入被观察者被观察者自上而下发射事件观察者模式 装饰器模式自上而下,被观察者...

  • 观察者模式

    观察者模式概念 观察者模式是对象的行为模式,又叫作发布-订阅(publish/subscrible)模式。 观察者...

  • 设计模式-观察者模式

    观察者模式介绍 观察者模式定义 观察者模式(又被称为发布-订阅(Publish/Subscribe)模式,属于行为...

  • 观察者模式

    观察者模式 观察者模式的定义 观察者模式(Observer Pattern)也叫做发布订阅模式(Publish/s...

  • iOS设计模式之观察者模式

    观察者模式 1、什么是观察者模式 观察者模式有时又被称为发布(publish)-订阅(Subscribe)模式、模...

  • 观察者模式和发布订阅模式区别

    观察者模式 所谓观察者模式,其实就是为了实现松耦合(loosely coupled)。 在观察者模式中,观察者需要...

网友评论

    本文标题:01.观察者模式

    本文链接:https://www.haomeiwen.com/subject/fndnhdtx.html