HeadFirst设计模式-观察者模式
观察者模式:定义了对象之间的一对多依赖,这样一来,当一个对象改变状态时,他的所有依赖者都会收到通知并自动更新。
Java代码
package b_ObserverPattern._02_weatherstation; public interface Subject { public void registerObserver(Observer o) ; public void removeObserver(Observer o); public void notifyObserver(); } //------------------------------------- package b_ObserverPattern._02_weatherstation; public interface Observer { public void update(float temp, float humidity, float pressure); } //------------------------------------- package b_ObserverPattern._02_weatherstation; 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); } @Override public void display() { System.out.println("Current conditions: " + temperature + "F degrees and " + humidity + "% humidity"); } @Override public void update(float temp, float humidity, float pressure) { this.temperature = temp; this.humidity = humidity; display(); } } //------------------------------------- package b_ObserverPattern._02_weatherstation; public class ForecastDisplay implements DisplayElement, Observer { private float temperature; private float humidity; private Subject weatherData; public ForecastDisplay(Subject weatherData) { this.weatherData = weatherData; weatherData.registerObserver(this); } @Override public void update(float temp, float humidity, float pressure) { this.temperature = temp; this.humidity = humidity; display(); } @Override public void display() { System.out.println("根据温度湿度预测天气。。。"); } } //------------------------------ package b_ObserverPattern._02_weatherstation; public class StatisticsDisplay implements DisplayElement, Observer { private float temperature; private float humidity; private Subject weatherData; public StatisticsDisplay(Subject weatherData) { this.weatherData = weatherData; weatherData.registerObserver(this); } @Override public void update(float temp, float humidity, float pressure) { this.temperature = temp; this.humidity = humidity; display(); } @Override public void display() { System.out.println("统计最大值、最小值、平均值"); } } //--------------------------------- package b_ObserverPattern._02_weatherstation; public interface DisplayElement { public void display(); } //------------------------------------- package b_ObserverPattern._02_weatherstation; import java.util.ArrayList; public class WeatherDate implements Subject { private ArrayList observers; private float temperature; private float humidity; private float pressure; public WeatherDate() { observers = new ArrayList(); } @Override public void registerObserver(Observer o) { observers.add(o); } @Override public void removeObserver(Observer o) { int i = observers.indexOf(o); if(i>=0) { observers.remove(i); } } @Override public void notifyObserver() { // for (int i = 0; i < observers.size(); i++) { // // } for (Object object : observers) { Observer observer = (Observer)object; observer.update(temperature, humidity, pressure); } } public void measurementsChanged() { notifyObserver(); } public void setMeasurements(float temperature, float humidity, float pressure) { this.temperature = temperature; this.humidity = humidity; this.pressure = pressure; measurementsChanged(); } } //------------------------------------- package b_ObserverPattern._02_weatherstation; public class WeatherStation { public static void main(String[] args) { WeatherDate weatherData = new WeatherDate(); CurrentConditionsDisplay conditionsDisplay = new CurrentConditionsDisplay(weatherData); Observer statisticsDisplay = new StatisticsDisplay(weatherData); ForecastDisplay forecastDisplay = new ForecastDisplay(weatherData); weatherData.setMeasurements(80, 65, 30.4f); weatherData.setMeasurements(82, 76, 32.9f); weatherData.setMeasurements(81, 70, 31.7f); } }
c++代码
#pragma once #include "Observer.h" class Subject { public: virtual void registerObserver(Observer* o) = 0; virtual void removeObserver(Observer* o) = 0; virtual void notifyObserver() = 0; }; //----------------------------------------- #pragma once #include <iostream> #include <string> using namespace std; class Observer { public: virtual void update(string arg) = 0; }; //----------------------------------------- #pragma once #include "Observer.h" #include "Subject.h" class CurrentConditionsDisplay : public Observer { Subject* subject; public: CurrentConditionsDisplay(Subject* sub) { subject = sub; subject->registerObserver(this); } ~CurrentConditionsDisplay() { } void update(string arg) { cout << "CurrentConditionsDisplay arg:" << arg << '\n'; } }; //----------------------------------------- #pragma once #include "Observer.h" #include "Subject.h" class ForecastDisplay : public Observer { Subject* subject; public: ForecastDisplay(Subject* sub) { subject = sub; subject->registerObserver(this); } ~ForecastDisplay() { } void update(string arg) { cout << "ForecastDisplay arg:" << arg << '\n'; } }; //----------------------------------------- #pragma once #include "Observer.h" #include "Subject.h" class StatisticsDisplay : public Observer { Subject* subject; public: StatisticsDisplay(Subject* sub) { subject = sub; subject->registerObserver(this); } ~StatisticsDisplay() { } void update(string arg) { cout << "StatisticsDisplay arg:" << arg << '\n'; } }; //----------------------------------------- #pragma once #include "Subject.h" #include <string> #include <vector> #include <algorithm> using namespace std; class WeatherData : public Subject { string temperature; string humidity; string pressure; vector<Observer*> observers; public: WeatherData() { } ~WeatherData() { } void registerObserver(Observer* o) { observers.push_back(o); } void removeObserver(Observer* o) { observers.erase(remove(observers.begin(), observers.end(), o)); } void notifyObserver() { for (int i = 0; i < observers.size(); i++) { Observer* pObj = observers.at(i); string arg = this->temperature + ";" + this->humidity + ";" + this->pressure; pObj->update(arg); } } void measurementsChanged() { notifyObserver(); } void setMeasurements(float temperature, float humidity, float pressure) { this->temperature = to_string(temperature); this->humidity = to_string(humidity); this->pressure = to_string(pressure); measurementsChanged(); } }; //----------------------------------------- #include <iostream> #include "CurrentConditionsDisplay.h" #include "ForecastDisplay.h" #include "StatisticsDisplay.h" #include "WeatherData.h" using namespace std; int main() { WeatherData data; CurrentConditionsDisplay d1(&data); ForecastDisplay d2(&data); StatisticsDisplay d3(&data); data.setMeasurements(13.2, 23, 31); data.setMeasurements(15.2, 28, 71); data.removeObserver(&d2); data.setMeasurements(17.2, 21, 61); return 0; } //-----------------------------------------
****
常记溪亭日暮,沉醉不知归路。兴尽晚回舟,误入藕花深处。争渡,争渡,惊起一滩鸥鹭。
昨夜雨疏风骤,浓睡不消残酒。试问卷帘人,却道海棠依旧。知否?知否?应是绿肥红瘦。