美文网首页基础
观察者模式

观察者模式

作者: 字字经心 | 来源:发表于2022-07-25 10:20 被阅读0次

    观察者模式

    现在有一个气象站,它是获取湿度、温度、气压数据的物理装置,WeatherData追踪气象站的数据变化,并且更新到报告班板,如图

    weather1.png

    需求:

    1. WeatherData 类有getter 方法,可以取得温度、湿度、气压、三个测量值。当测量数据发送变化时,WeatherData measurementsChanged() 方法就会被调用(先不管它是如何被调用的,只要记住一点数据变化会调用此方法)
    2. 需要实现三个布告板,目前状况布告、气象统计布告、天气预报布告;并且系统需可扩展,实现让其他开发人员建立定制的布告板,用户可以随便添加或者删除 任何布告板
    weather2.png

    一般我们是这样实现的

    public class WeatherData {
        // 实例变量声明
        pubic void measuremetnsChanged(){
            float temp = getTemperature();
            float humidity = getHumidity();
            float pressure = getPressure();
            
            currentConditionsDisplay.update(temp, humidity, pressure);
            statisticsDisplay.update(temp, humidity, pressure);
            forecastDisplay.update(temp, humidity, pressure);
        }
        
        // 这里WeatherData 其他方法
    }
    

    这样实现由缺点

    • 对于每个新的布告板,我们都得修改代码,我们尚未封装改变的部分
    • 布告板没有实现一个共同的 接口,至少update 看来参数没有发生变化
    • 我们无法在运行时动态地添加、删除布告板

    利用观察者模式来设计,观察者模式就类似在生活中我们 向杂志社订阅或者取消订阅报纸、杂志。结合模型对象的编程思想,杂志社需要提供 订阅、取消订阅、通知用户的方法,而订阅者肯定要提供一个 让杂志社联系上自己的方法。联系上面的需求,画出类图

    weather3.png

    所以我们可以把实现上面需求的类图设计为

    weather4.png

    实现代码如下

    public interface Subject {
        public void registerObserver(Observer o);
        public void removeObserver(Observer o);
        public void notifybservers();
    }
    
    public interface Observer {
        public void update(float temp, float humidity, float pressure);
    }
    
    public interface DisplayElement{
        public void display();
    }
    
    // 实现 weatherData
    public class WeatherData implements Subject {
        private ArrayList observers;
        private float temperature;
        private float humidity;
        private float pressure;
        
        public WeatherData(){
            observers = new ArrayList();
        }
        
        public void registerObserver(Observer o){
            observers.add(o);
        }
        
        public void removeObserver(Observer o){
            int i = observers.indexof(o);
            if(i >= 0){
                observer.remove(i);
            }
        }
        
       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(){
           notifyObservers();
       }
    }
    
     // 创建布告板
     public class CurrentconditionsDisplay implements Observer, DisplayElement {
        private float temperature;
        private float humidity;
        private Subject weatherData;
    
        public CurrentconditionsDisplay(Subject weatherdata){
            this.weatherData = weatherData;
            weatherData.registerobserver(this);
        }
        
        public void update (float temperature, float humidity, float pressure) {
            this.temperature = temperature;
            this.humidity = humidity;
            display();
        }
        
        public void display(){
          // ....
        }
    }
    
    

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

    相关文章

      网友评论

        本文标题:观察者模式

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