观察者模式(Observer Pattern)

观察者模式又叫做订阅/发布模式

  • 一个Subject,多Observer
  • 相互之间持有引用
  • Subject可以调用Observer的函数执行相应操作
  • Observer发生变动时也可以通知Subject让其通知其他观察者。

给个小栗子(效果图如下)

目标被观察者

 1 package ObserverPattern;
 2 
 3 import java.util.ArrayList;
 4 import java.util.List;
 5 
 6 public abstract class Subject {
 7 
 8     //define an ArrayList to store observers
 9     private List<Observer>  observers = new ArrayList<>();
10     public List<Observer> getObservers() {
11         return observers;
12     }
13 
14 
15     public void join(Observer observer) {
16         observers.add(observer);
17     }
18 
19     public void quit(Observer observer) {
20         observers.remove(observer);
21     }
22 
23     public abstract void notifyObservers(String name);
24 
25 }
View Code

观察者

package ObserverPattern;

public abstract class Observer {
    protected Subject subject;
    public Observer(Subject subject) {
        this.subject = subject;
    }
    public abstract void sysMsg(String msg);
    public abstract void beAttacked();

    public abstract String getName();
    public abstract void setName(String name);
}
View Code

战况指挥中心

package ObserverPattern;

public class ActionControlCenter extends Subject {
    @Override
    public void notifyObservers(String name) {
        for (Observer observer : getObservers()) {
            if (name.equals(observer.getName()))
                observer.sysMsg(observer.getName() +"收到消息:坚持住,你队友正在赶来!");
            else
                observer.sysMsg(observer.getName() +"收到消息:我方"" + name + ""正在受到攻击,请尽快支援!");
        }
    }
}
View Code

玩家

package ObserverPattern;

public class Player extends Observer {

    public Player(Subject subject) {
        super(subject);
    }

    private String name;
    public void setName(String name) {
        this.name = name;
    }
    public String getName() {
        return name;
    }

    @Override
    public void beAttacked() {
        System.out.println(getName() + "收到消息:您正在受到攻击!");
        subject.notifyObservers(getName());
    }
    @Override
    public void sysMsg(String msg) {
        System.out.println(msg);
    }
}
View Code

测试用例

package ObserverPattern;

import org.junit.Test;

public class MainTest {

    @Test
    public void myTest() {

        ActionControlCenter controlCenter = new ActionControlCenter();

        Player p1 = new Player(controlCenter);
        Player p2 = new Player(controlCenter);
        p1.setName("邓艾");
        p2.setName("甄姬");


        controlCenter.join(p1);
        controlCenter.join(p2);

        p2.beAttacked();
    }

}
原文地址:https://www.cnblogs.com/webyyq/p/9102017.html