Java設計模式——行爲型模式之觀察者模式

一、前言

      在生活中我們會遇到這樣的場景:用水壺燒開水。當水燒開時,你會有一個關火的過程。在燒水的過程中,你一直觀察着這個燒水的進度,當它的狀態改變時會觸發你關火的這個動作。觀察者模式就是處理這種場景而設計出來的一種設計模式。

二、觀察者模式

概述: 定義對象間的一種一對多的依賴關係,當一個對象的狀態發生改變時,所有依賴於它的對象都得到通知並被自動更新。

觀察者模式是爲了處理一個對象狀態改變給其他對象通知的問題,而且要考慮到易用和低耦合,保證高度的協作。

使用場景:

1.    當一個抽象模型有兩個方面,其中一個方面依賴於另一方面。 將這二者封裝在獨立的對象中以使它們可以各自獨立地改變和複用。

2、當對一個對象的改變需要同時改變其它對象,而不知道具體有多少對象有待改變。

3、當一個對象必須通知其它對象,而它又不能假定其它對象是誰。

簡而言之觀察者模式就是處理兩個相互依賴對象的耦合關係。

優點: 1、觀察者和被觀察者是抽象耦合的。 2、建立一套觸發機制。

缺點:1、如果觀察者過多會導致通知觀察者時間過長,從而導致系統的性能下降。

三、代碼展示

   我們通過一個警察出巡的例子來演示觀察者 模式。

3.1 定義一個目標接口,這個接口裏需要存放觀察者,通常都用一個list來存放這些觀察者,並提供對這些觀察者進行註冊、刪除的方法。

public abstract class Citizen {
    
    List pols;
    
    String help = "normal";
    
    public void setHelp(String help) {
        this.help = help;
    }
    
    public String getHelp() {
        return this.help;
    }
    
    abstract void sendMessage(String help);

    public void setPolicemen() {
        this.pols = new ArrayList();
    }
    
    public void register(Policeman pol) {
        this.pols.add(pol);
    }

    public void unRegister(Policeman pol) {
        this.pols.remove(pol);
    }
}
3.2 定義警察這個觀察者
public interface Policeman {

    void action(Citizen ci);
}
3.3 實現目標接口

public class HuangPuCitizen extends Citizen {

    public HuangPuCitizen(Policeman pol) {
        setPolicemen();
        register(pol);
    }
    
    public void sendMessage(String help) {
        setHelp(help);
        for(int i = 0; i < pols.size(); i++) {
            Policeman pol = pols.get(i);
            //通知警察行動
            pol.action(this);
        }
    }
}
public class TianHeCitizen extends Citizen {

    public TianHeCitizen(Policeman pol) {
        setPolicemen();
        register(pol);
    }
    
    public void sendMessage(String help) {
        setHelp(help);
        for (int i = 0; i < pols.size(); i++) {
            Policeman pol = pols.get(i);
            //通知警察行動
            pol.action(this);
        }
    }
}

3.4 實現觀察者接口

public class HuangPuPoliceman implements Policeman {

    public void action(Citizen ci) {
        String help = ci.getHelp();
        if (help.equals("normal")) {
            System.out.println("一切正常, 不用出動");
        }
        if (help.equals("unnormal")) {
            System.out.println("有犯罪行爲, 黃埔警察出動!");
        }
    }
}
public class TianHePoliceman implements Policeman {

    public void action(Citizen ci) {
        String help = ci.getHelp();
        if (help.equals("normal")) {
            System.out.println("一切正常, 不用出動");
        }
        if (help.equals("unnormal")) {
            System.out.println("有犯罪行爲, 天河警察出動!");
        }
    }
}

3.5 結果展示

public class Test{

    public static void main(String[] args) {
        Policeman thPol = new TianHePoliceman();
        Policeman hpPol = new HuangPuPoliceman();
        
        Citizen citizen = new HuangPuCitizen(hpPol);
        citizen.sendMessage("unnormal");
        citizen.sendMessage("normal");
        
        System.out.println("===========");
        
        citizen = new TianHeCitizen(thPol);
        citizen.sendMessage("normal");
        citizen.sendMessage("unnormal");
    }
}
有犯罪行爲, 黃埔警察出動!
一切正常, 不用出動
===========
一切正常, 不用出動
有犯罪行爲, 天河警察出動!

我們可以發現,在這個例子中,觀察者和目標都做了抽象,這樣做可以降低觀察者和目標的耦合度。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章