设计模式之内容观察者模式

一:定义观察者模式

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

二:观察者模式类图:




三:观察者模式的自我理解:

  (1)<<interface>>Observer: 定义了观察者更新的操作接口

  (2)<<interface>>Subject:定义了对象的注册,注销和通知数据更新的三个接口

   (3)ConcreteObserver类,主要是实现了<<interface>>Observer的更新操作

   (4)ConcreteSubject类,我们也可以称管理类,主要是实现了<<interface>>Subject定义的注册,注销和通知数据更新的三个接口,其中的一个关键变量-List<ConcreteObserver> concreteObserver,这个变量主要是对所有的观察者进行管理,当数据改变时,遍历所有的观察者,进行相对应的操作。


四:我的一个小例子:

   这个例子是Head First设计模式(中文版)这本书中最后的一个小程序,我在android上实现了。这个例子是当我点击一个按键时,有二个观察者,一个观察者(天使)会说:亲,我是天使,我对于您的点击,我的答复是:我爱你!!,另一个观察者(恶魔)会说:亲,我是恶魔,我对于您的点击,我的答复是:我恨你!!

   在这个例子中,我应用了单例模式,观察者模式。


(1)<<interface>>Observer:

public interface IClickListernObserver {
	public void onClickToUpdate();
}

(2)ConcreteObserver类-----AngelObserver:

public class AngelObserver implements IClickListernObserver {
	
	private static AngelObserver instance;
	
	private IAngelClickLister myIAngelClickLister;
	
	public AngelObserver(){
		ClickListerManager.getInstance().registerObserver(this);
	}

	
	public static AngelObserver getInstance(){
		if(instance == null)
			instance = new AngelObserver();
		return instance;
	}
	
	public void setMyIAngelClickLister(IAngelClickLister myIAngelClickLister){
		this.myIAngelClickLister = myIAngelClickLister;
	}
	
	@Override
	public void onClickToUpdate() {
		// TODO Auto-generated method stub
		myIAngelClickLister.onClickAngelDo();
	}
	
	public interface IAngelClickLister{
		public void onClickAngelDo();		
	}
	
}

(3)ConcreteObserver类-----DevilObserver :

public class DevilObserver implements IClickListernObserver {
	
	private static DevilObserver instance;
	
	private IDevilClickLister myIDevilClickLister;
	
	public DevilObserver(){
		ClickListerManager.getInstance().registerObserver(this);
	}

	
	public static DevilObserver getInstance(){
		if(instance == null)
			instance = new DevilObserver();
		return instance;
	}
	
	public void setMyIDevilClickLister(IDevilClickLister myIDevilClickLister){
		this.myIDevilClickLister = myIDevilClickLister;
	}
	
	@Override
	public void onClickToUpdate() {
		// TODO Auto-generated method stub
		myIDevilClickLister.onClickDevilDo();
	}
	
	public interface IDevilClickLister{
		public void onClickDevilDo();		
	}	
	
}

(4)<<interface>>Subject:

public interface Subject {
	public void registerObserver(IClickListernObserver o);
	public void unRegisterObserver(IClickListernObserver o);
	public void notifyObservers();
}

(5)ConcreteSubject类:

import java.util.ArrayList;
import java.util.List;

public class ClickListerManager implements Subject {
	
	private static ClickListerManager instance;
	
	private List<IClickListernObserver> observers;

	public ClickListerManager(){
		observers = new ArrayList<IClickListernObserver>();
	}
	
	public static ClickListerManager getInstance(){
		if(instance == null)
			instance = new ClickListerManager();
		return instance;
	}
	
	public void notifyAllItem(){
		notifyObservers();
	}
	
	@Override
	public void registerObserver(IClickListernObserver object) {
		// TODO Auto-generated method stub
		if(!observers.contains(object)){
			observers.add(object);					
		}	
	}

	@Override
	public void unRegisterObserver(IClickListernObserver object) {
		// TODO Auto-generated method stub
		if(observers.contains(object)){
			observers.remove(object);				
		}		
	}

	@Override
	public void notifyObservers() {
		// TODO Auto-generated method stub
		for(int i = 0;i < observers.size();i++){
			observers.get(i).onClickToUpdate();
		}
	}
}

(6)ContentObserverActivity类:

import com.example.testcontentobserver01.AngelObserver.IAngelClickLister;
import com.example.testcontentobserver01.DevilObserver.IDevilClickLister;
import android.os.Bundle;
import android.app.Activity;
import android.view.Menu;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.TextView;

public class ContentObserverActivity extends Activity implements OnClickListener,
											IAngelClickLister, IDevilClickLister{
	
	private Button myButton;
	private TextView myTextViewAngel;
	private TextView myTextViewDevil;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_content_observer);	
		init();	
		myButton = (Button) findViewById(R.id.myButton);
		myButton.setOnClickListener(this);		
		myTextViewAngel = (TextView) findViewById(R.id.myTextViewAngel);
		myTextViewDevil = (TextView) findViewById(R.id.myTextViewDevil);
	}

	private void init() {
		// TODO Auto-generated method stub
		AngelObserver.getInstance();
		AngelObserver.getInstance().setMyIAngelClickLister(this);
		DevilObserver.getInstance();
		DevilObserver.getInstance().setMyIDevilClickLister(this);
	}

	@Override
	public void onClick(View view) {
		// TODO Auto-generated method stub
		int id = view.getId();
		switch(id){
			case R.id.myButton:
				ClickListerManager.getInstance().notifyAllItem();			
		}
	}

	@Override
	public void onClickAngelDo() {
		// TODO Auto-generated method stub
		myTextViewAngel.setText("亲,我是天使,我对于您的点击,我的答复是:我爱你!!");
	}

	@Override
	public void onClickDevilDo() {
		// TODO Auto-generated method stub
		myTextViewDevil.setText("亲,我是恶魔,我对于您的点击,我的答复是:我恨你!!");
	}

}

五:气象监测应用

   这个例子也是Head First设计模式(中文版)这本书中的说明样例,这个例子是现在有三个显示装置,一个要显示气象站的温度,一个显示湿度,一个显示气压,并且当这三个数据有改变时,要实时的更新三个显示装置,并且还要方便以后增加显示装置。

   解决方案是观察者模式:

  (1)类图:



(2)interface Subject:

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

(3)interface Observer:

public interface Observer{
  public void update(float temp,float humidity,float pressure);
}

(4)interface DisplayElement:

public interface DisplayElement{
  public void display();
}

(5)WeatherData 类:

public class WeatherData implements Subject{
  private ArrayList observers;
  private float temperature;
private float humidity;
private float pressure;

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

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

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

public void measurementsChanged(){
  notifyObservers();
}

public void setMeasurements(float temperature, float humidity, float pressure){
  this. temperature = temperature;
  this. humidity = humidity;
  this. pressure = pressure;
  measurementsChanged();
}
………………….
}

(6)类CurrentConditionsDisplay:

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(){
  System.out.println(“Current conditions:” + temperature + “F degrees and ” + humidity + “% humidity”);
}
}


(7)相类似的,我们可以实现StatisticsDisplay,ForecastDisplay二个类
省略


(8)测试类:

public class WeatherStation{
  public static void main(String[] args){
WeatherData weatherData = new WeatherData();
CurrentConditionsDisplay currentDisplay = new CurrentConditionsDisplay(weatherData);
StatisticsDisplay statisticsDisplay = new StatisticsDisplay(weatherData); 
ForecastDisplay forecastDisplay = new ForecastDisplay (weatherData); 

weatherData. setMeasurements(80,65,30.4f);
weatherData. setMeasurements(70,75,31.4f);
weatherData. setMeasurements(90,55,32.4f);
  }
}


参考资料:

1.http://blog.csdn.net/hfreeman2011/article/details/8308873
2.Head First设计模式(中文版),中国电力出版社出版,O‘REILLY公司译----(39--78页)观察者模式

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

hfreeman2008

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值