题目
气象局需要我们构建一套系统,这系统有两个公告牌,分别用于显示当前的实时天气和未来几天的天气预报。当气象局发布新的天气数据(WeatherData)后,两个公告牌上显示的天气数据必须实时更新。气象局同时要求我们保证程序拥有足够的可扩展性,因为后期随时可能要新增新的公告牌。
概况
这套系统中主要包括三个部分:气象站(获取天气数据的物理设备)、WeatherData(追踪来自气象站的数据,并更新公告牌)、公告牌(用于展示天气数据)
WeatherData知道如何跟气象站联系,以获得天气数据。当天气数据有更新时,WeatherData会更新两个公告牌用于展示新的天气数据。
结构
/**
* 主题
* */
public interface Subject {
/**
* 注册观察者
* */
void registerObserver(Observer obserber);
/**
* 移除观察者
**/
void removeObserber(Observer obserber );
/**
* 通知
* */
void notifyObserbers();
public class WeatherData implements Subject {
private List<Observer> obserbers;
private float temperature; // 温度
private float pressure; // 气压
private List<Float> forecastTemperatures; // 未来几天的温度
public WeatherData() {
this.obserbers = new ArrayList<Observer>();
}
@Override
public void registerObserver(Observer obserber) {
obserbers.add(obserber);
}
@Override
public void removeObserber(Observer obserber) {
obserbers.remove(obserber);
}
@Override
public void notifyObserbers() {
Iterator<Observer> iterator = obserbers.iterator();
while (iterator.hasNext()) {
Observer observer = iterator.next();
observer.update();
}
}
public void measurementsChanged() {
notifyObserbers();
}
public void setMeasurements(float temperature, float pressure, List<Float> forecastTemperatures) {
this.temperature = temperature;
this.pressure = pressure;
this.forecastTemperatures = forecastTemperatures;
measurementsChanged();
}
public List<Observer> getObserbers() {
return obserbers;
}
public void setObserbers(List<Observer> obserbers) {
this.obserbers = obserbers;
}
public float getTemperature() {
return temperature;
}
public void setTemperature(float temperature) {
this.temperature = temperature;
}
public float getPressure() {
return pressure;
}
public void setPressure(float pressure) {
this.pressure = pressure;
}
public List<Float> getForecastTemperatures() {
return forecastTemperatures;
}
public void setForecastTemperatures(List<Float> forecastTemperatures) {
this.forecastTemperatures = forecastTemperatures;
}
}
/**
* 观察者
* */
public interface Observer {
/**
* 更新
* */
void update();
}
/**
* 公告牌
* */
public interface DisplayElement {
/**
*展示
* */
public void display();
}
public class CurrentConditionsDisplay implements Observer , DisplayElement {
private WeatherData weatherData ;
private float temperature ; //湿度
private float pressure; // 气压
public CurrentConditionsDisplay (WeatherData weatherData ) {
this.weatherData = weatherData ;
this.weatherData.registerObserver(this);
}
@Override
public void update() {
this.temperature = this.weatherData.getTemperature();
this.pressure = this.weatherData.getPressure();
display();
}
@Override
public void display() {
System.out.println("当前湿度:" + this.temperature );
System.out.println("当前气压:" + this.pressure );
}
}
public class ForecastDisplay implements Observer, DisplayElement {
private WeatherData weatherData ;
private List<Float> forecastTemperatures ;
public ForecastDisplay(WeatherData weatherData) {
this.weatherData = weatherData ;
this.weatherData.registerObserver(this);
}
@Override
public void display() {
System.out.println("未来几天气温:");
int count = forecastTemperatures.size() ;
for(int i = 0 ; i < count ; i++) {
System.out.println("第"+ i + "天,气温:" + forecastTemperatures.get(i) + "℃");
}
}
@Override
public void update() {
this.forecastTemperatures = weatherData.getForecastTemperatures() ;
display();
}
}
测试类
public class Test {
public static void main(String[] args) {
List<Float> forecastTemperatures = new ArrayList<>();
forecastTemperatures.add((float) 28);
forecastTemperatures.add((float) 32);
forecastTemperatures.add((float) 30);
WeatherData whatherData = new WeatherData();
whatherData.setTemperature(32);
whatherData.setPressure(15);
whatherData.setForecastTemperatures(forecastTemperatures);
CurrentConditionsDisplay currentConditionsDisplay = new CurrentConditionsDisplay(whatherData);
ForecastDisplay forecastDisplay = new ForecastDisplay(whatherData);
System.out.println("-------whatherData初始化-------");
currentConditionsDisplay.update();
forecastDisplay.update();
System.out.println("-------whatherData数据更改-------");
forecastTemperatures.clear();
forecastTemperatures.add((float) 29);
forecastTemperatures.add((float) 33);
forecastTemperatures.add((float) 31);
whatherData.setMeasurements(33, 16, forecastTemperatures);
}
}
运行结果:
-------whatherData初始化-------
当前湿度:32.0
当前气压:15.0
未来几天气温:
第0天,气温:28.0℃
第1天,气温:32.0℃
第2天,气温:30.0℃
-------whatherData数据更改-------
当前湿度:33.0
当前气压:16.0
未来几天气温:
第0天,气温:29.0℃
第1天,气温:33.0℃
第2天,气温:31.0℃