观察者设计模式(observer)

Observer(观察者)模式是比较常用的一个模式,他让主题和观察者之间松耦合

定义:定义对象间一对多的依赖,这样一来,当一个对象发生改变,其他依赖者会得到通知并自动更新.

作为观察者,主题只知道他实现一个接口Oberver,主题不需要知道他具体是谁,需要实现什么操作.

任何时候我们都可以增加新的观察者.因为主题实现的是一个实现oberver的抽象接口列表,所以我们可以随时增加和删除观察者

主题不用了解其他的,只需要给现有注册的观察者发消息就可以了,观察者的增加和改变,不需要修改主题的代码.

主题和观察者,我们可以重复使用,改变一方不会影响另外一方,说到底就是为了达到解耦合的目的.

应用场合:

新京报,他是一个主题,很多人都可以定购他,他不需要了解你订购他是干吗,他只知道你付了钱,他给你一份报纸,到什么地址.如果他修改版面,他会通知你,比如说,最近物价上涨.可能需要上涨几毛钱.(有更改就会通知依赖者)

而订购他的人或者公司,属于观察者也就是依赖者,只有2个参数,一个是注册,一个是解除注册.注册后,就会收到报纸的最新消息,一有修改就会通知你.解除注册后,你还是你,但是你已经不属于依赖者了,就不会接到相应的消息.你可以今天注册,今天解除(这是你的事情).不会影响到其他的东西,也就是松耦合.


首先我们来模拟JDK里面有自带的类实现观察者模式:

实现一个电脑厂商和地区代理的示例,一对多关系依赖

GeneralProxy.java

package com.linpyi.computer;

/** 
 * 电脑总代理接口 
 * @author work 
 * 
 */  
public interface GeneralProxy {  
    /** 
     * 注册电脑代理 
     * @param o 
     */  
    public void registerComputerProxy(Observer o);  
    /** 
     * 移除电脑代理 
     * @param o 
     */  
    public void removeComputerProxy(Observer o);  
    /** 
     * 更新代理价格 
     */  
    public void notifyComputerProxy();  
}  

Observer.java

package com.linpyi.computer;  
  
/** 
 * 电脑观察者,自己写的代理接口 
 * @author work 
 * 
 */  
public interface Observer {  
    /** 
     * 更新电脑信息 
     * @param name 电脑品牌 
     * @param price 电脑价格 
     * @param info 电脑描述 
     */  
    public void update(String name,float price,String info);  
}

BranchProxy.java

package com.linpyi.computer;  
/** 
 * 电脑分代理接口 
 * @author work 
 * 
 */  
public interface BranchProxy {  
    /** 
     * 默认方法 
     */  
    public void display();  
}  
LenvoComputer.java

package com.linpyi.computer;  
  
import java.util.ArrayList;  
  
/** 
 * lenovo电脑
 * @author work 
 * 
 */  
public class LenvoComputer implements GeneralProxy {  
      
    private ArrayList proxys ;  
    private String name;  
    private float price;  
    private String info;  
      
    public LenvoComputer(){  
        proxys = new ArrayList();  
    }
      
    /** 
     * 更改lenvo分代理的信息 
     */  
    public void notifyComputerProxy() {  
        for(int i = 0 ;i<proxys.size();i++){  
            Observer proxy = (Observer)proxys.get(i);  
            proxy.update(name, price, info);
        }
    }
      
    /** 
     * 设置lenvo的电脑价格和信息 
     * @param name 电脑名称 
     * @param price 电脑价格 
     * @param info 电脑描述信息 
     */  
    public void setLenvo(String name,float price,String info){  
        this.name=name;  
        this.price=price;  
        this.info=info;  
        notifyComputerProxy();  
    }
  
    /** 
     * 注册lenvo代理 
     */  
    public void registerComputerProxy(Observer o) {  
        proxys.add(o);  
    }  
  
    /** 
     * 移除lenvo代理 
     */  
    public void removeComputerProxy(Observer o) {  
        // TODO Auto-generated method stub  
        int i = proxys.indexOf(o);  
        if(i>=0){  
            proxys.remove(o);  
        }  
    }
}  

ChinaProxy.java

package com.linpyi.computer;  
  
/** 
 * 中国地区代理类,使用自己写的代理接口 
 * @author  
 * 
 */  
public class ChinaProxy implements BranchProxy, Observer {  
      
    private GeneralProxy generalProxy;  
    private String name ;  
    private float price;  
    private String info;  
      
    public ChinaProxy(GeneralProxy generalProxy){  
        this.generalProxy=generalProxy;  
        generalProxy.registerComputerProxy(this);//注册代理  
    }  
  
    /** 
     * 默认方法 
     */  
    public void display() {  
        // TODO Auto-generated method stub  
        System.out.println("中国代理");  
        System.out.println("型号"+name);  
        System.out.println("价格"+price);  
        System.out.println("描述信息"+info);  
    }  
  
    /** 
     * 更新方法 
     */  
    public void update(String name, float price, String info) {  
        // TODO Auto-generated method stub  
        this.name=name;  
        this.price=price;  
        this.info=info;  
        display();  
    }  
  
}  

JapanProxy.java

package com.linpyi.computer;  
  
/** 
 * 日本代理,使用自己写的代理接口 
 *  
 * @author work 
 *  
 */  
public class JapanProxy implements BranchProxy, Observer {  
  
    private String name;  
    private String info;  
    private float price;  
    private GeneralProxy generalProxy;
  
    public JapanProxy(GeneralProxy generalProxy) {  
        this.generalProxy = generalProxy;  
        generalProxy.registerComputerProxy(this);  
    }  
  
    public void update(String name, float price, String info) {  
        this.name = name;  
        this.price = price;  
        this.info = info;  
        display();  
    }
  
    public void display() {  
        // TODO Auto-generated method stub  
        System.out.println("日本代理");  
        System.out.println("型号" + name);  
        System.out.println("价格" + price);  
        System.out.println("描述信息" + info);  
    }
}  
Client.java

package com.linpyi.computer;

public class Client {

    public static void main(String[] args){  
        //使用自己写的观察模式方法  
        LenvoComputer lenvo = new LenvoComputer();  
        ChinaProxy chinaProxy  = new ChinaProxy(lenvo);  
        JapanProxy japanProxy  = new JapanProxy(lenvo);  
        lenvo.setLenvo("lenvo0001", 8000, "disk 160G , memory 2G");  

    }
}    
使用JDK里面有自带的类实现观察者模式:

HpComputer.java

package com.linpyi.computer;  
  
import java.util.Observable;  
  
/** 
 * HP电脑代理,使用的是JDK自带的观察者模式类(Observable) 
 * @author work 
 * 
 */  
public class HpComputer extends Observable {  
  
    private String name;  
    private float price;  
    private String info;  
      
    public void measurementsChanged(){  
        setChanged();//观察者类里的方法,主要用于开关  
        notifyObservers();//继承类里的方法(通知观察者)  
    }  
      
    public void setMeasurements(String name,float price,String info){  
        this.name=name;  
        this.price=price;  
        this.info=info;  
        measurementsChanged();  
    }  
      
    public String getName(){  
        return name;  
    }  
      
    public float getPrice(){  
        return price;  
    }  
      
    public String getInfo(){  
        return info;  
    }  
    

}  

IndiaProxy.java

package com.linpyi.computer;  
  
import java.util.Observable;  
import java.util.Observer;  
  
/** 
 * 印度电脑代理(使用JDK自带的接口) 
 * @author work 
 * 
 */  
public class IndiaProxy implements Observer, BranchProxy {  
      
    private Observable observable;  
    private String name;  
    private String info;  
    private float price;  
      
    public IndiaProxy(Observable observable) {  
        this.observable = observable;  
        observable.addObserver(this);//增加观察者(JDK自带的)  
    }  
  
    /** 
     * 更新方法,使用的是JDK自带的方法 
     */  
    public void update(Observable o, Object arg) {  
        // TODO Auto-generated method stub  
        if (o instanceof HpComputer) {  
            HpComputer computer = (HpComputer) o;  
            this.name = computer.getName();  
            this.price = computer.getPrice();  
            this.info = computer.getInfo();  
            display();  
        }  
    }  
  
    public void display() {  
        // TODO Auto-generated method stub  
        System.out.println("印度代理");  
        System.out.println("型号" + name);  
        System.out.println("价格" + price);  
        System.out.println("描述信息" + info);  
    }  
  
}  

KoreaProxy.java

package com.linpyi.computer;  
  
import java.util.Observable;  
import java.util.Observer;  
  
/** 
 * 韩国代理,使用的是JDK自带的接口(Observer) 
 * @author work 
 * 
 */  
public class KoreaProxy implements Observer, BranchProxy {  
    private Observable observable;  
    private String name;  
    private String info;  
    private float price;  
  
    public KoreaProxy(Observable observable) {  
        this.observable = observable;  
        observable.addObserver(this);  
    }
  
    public void update(Observable o, Object arg) {  
        // TODO Auto-generated method stub  
        if (o instanceof HpComputer) {  
            HpComputer computer = (HpComputer) o;  
            this.name = computer.getName();  
            this.price = computer.getPrice();  
            this.info = computer.getInfo();  
            display();  
        }  
    }  
  
    public void display() {  
        // TODO Auto-generated method stub  
        System.out.println("韩国代理");  
        System.out.println("型号" + name);  
        System.out.println("价格" + price);  
        System.out.println("描述信息" + info);  
    }  
  
}  

Client.java

package com.linpyi.computer;

public class Client {

    public static void main(String[] args){  
    	//使用JDK的观察模式方法  
    	HpComputer hp = new HpComputer();  
    	KoreaProxy koreaProxy = new KoreaProxy(hp);  
    	IndiaProxy IndiaProxy = new IndiaProxy(hp);  
    	hp.setMeasurements("hp0001", 7000, "disk 250G , memory 10G");  

    }
}       

JDK里面有自带的类实现观察者模式,在java.util.Observable,注意这是类而不是接口,类有类的局限性,因为JAVA只能继承


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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值