设计模式——观察者模式

观察者模式(Observer Pattern)是一种行为型设计模式,它定义了对象之间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都会得到通知并被自动更新。

原理

  • 主题(Subject/发布者): 提供注册和移除观察者的接口,并且在自身状态变化时负责通知所有已注册的观察者。
  • 具体主题(Concrete Subject): 具体实现主题类,通常包含具体的业务逻辑及状态,并持有观察者列表。
  • 观察者(Observer): 定义了一个更新接口,当接收到主题的通知时调用此接口进行相应的操作。
  • 具体观察者(Concrete Observer): 实现观察者接口,其中包含了根据主题状态变化需要做出反应的具体方法。

Java代码示例

java 复制代码
// 观察者接口
import java.util.ArrayList;
import java.util.List;

public interface Observable {
    void addObserver(Observer observer);
    void removeObserver(Observer observer);
    void notifyObservers(String message);
}

// 具体主题类
public class NewsAgency implements Observable {
    private List<Observer> observers = new ArrayList<>();
    private String news;

    @Override
    public void addObserver(Observer observer) {
        observers.add(observer);
    }

    @Override
    public void removeObserver(Observer observer) {
        observers.remove(observer);
    }

    @Override
    public void notifyObservers(String message) {
        for (Observer observer : observers) {
            observer.update(message);
        }
    }

    public void setNews(String news) {
        this.news = news;
        // 发布新消息时,通知所有观察者
        notifyObservers(news);
    }
}

// 观察者接口
public interface Observer {
    void update(String message);
}

// 具体观察者类
public class Newspaper implements Observer {
    private String name;

    public Newspaper(String name) {
        this.name = name;
    }

    @Override
    public void update(String message) {
        System.out.println(name + " received news: " + message);
        // 在这里执行实际的消息处理逻辑
    }
}

// 客户端使用示例
public class Client {
    public static void main(String[] args) {
        NewsAgency agency = new NewsAgency();
        Observer newspaper1 = new Newspaper("The Daily");
        Observer newspaper2 = new Newspaper("The Times");

        agency.addObserver(newspaper1);
        agency.addObserver(newspaper2);

        agency.setNews("Breaking news!");  // 当发布新消息时,会自动通知所有报纸
    }
}

想象你是一个新闻机构,有很多家报纸订阅你的新闻。每次有新的新闻时,你需要逐一打电话给每一家报纸告诉他们最新消息。在程序世界里,新闻机构就是"主题",而各家报纸是"观察者"。当新闻机构有新消息时,只需调用notifyObservers()方法,就像打一圈电话一样,所有订阅的报纸(观察者)就会自动得到通知并更新自己的内容。

应用

  • 事件驱动编程:如GUI应用中按钮点击事件触发的响应处理。
  • 订阅系统:用户订阅新闻、博客或邮件提醒,当有新内容发布时,系统自动发送通知给所有订阅者。
  • 数据同步:多个模块需要共享同一份数据源,当数据源发生变化时,各模块能够及时得到更新。

适用性

  • 当一个对象的改变需要同时改变其他对象,而且不知道具体有多少对象需要改变时。
  • 当一个对象必须通知其他对象,而并不希望指定这些对象或这些对象只知道有改变发生,而不关心如何得知这一改变时。
相关推荐
浮游本尊37 分钟前
Java学习第22天 - 云原生与容器化
java
渣哥2 小时前
原来 Java 里线程安全集合有这么多种
java
间彧3 小时前
Spring Boot集成Spring Security完整指南
java
间彧3 小时前
Spring Secutiy基本原理及工作流程
java
数据智能老司机4 小时前
精通 Python 设计模式——创建型设计模式
python·设计模式·架构
Java水解4 小时前
JAVA经典面试题附答案(持续更新版)
java·后端·面试
数据智能老司机5 小时前
精通 Python 设计模式——SOLID 原则
python·设计模式·架构
洛小豆6 小时前
在Java中,Integer.parseInt和Integer.valueOf有什么区别
java·后端·面试
前端小张同学6 小时前
服务器上如何搭建jenkins 服务CI/CD😎😎
java·后端
ytadpole7 小时前
Spring Cloud Gateway:一次不规范 URL 引发的路由转发404问题排查
java·后端