当前位置: 首页 > news >正文

设计模式:观察者模式

        观察者模式(Observer Pattern)是一种行为设计模式,它定义了对象之间的一对多依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都会得到通知并被自动更新。这种模式通常被用来实现事件处理系统、实时数据更新、状态监控等多种场景。

关键组件:

  1. Subject(主题/被观察者):它是被观察的对象,负责维护一个观察者列表,并在状态发生改变时通知所有的观察者。Subject通常会提供注册(attach)、注销(detach)观察者以及通知(notify)观察者的方法。

  2. Observer(观察者):它是观察主题状态变化的对象,提供一个更新自己的方法(通常称为update)。当Subject状态变化时,它会调用所有已注册的Observer的update方法。

工作流程:

  1. 注册过程:观察者向主题注册自己,表明自己对主题状态变化感兴趣。
  2. 状态改变:当主题状态发生改变时,它会自动通知所有已注册的观察者。
  3. 更新操作:每个观察者接收到通知后,根据收到的信息执行相应的操作来更新自己的状态。

优点:

  • 松耦合:主题和观察者之间仅通过接口关联,降低了模块间的耦合度,使得两者可以独立地变化。
  • 扩展性:可以轻松地增加新的观察者,而无需修改主题或其他现有的观察者代码。
  • 灵活性:能够支持广播通信,即一个主题状态的改变可以通知多个观察者。

实现示例(Java):

        以下是使用Java实现观察者模式的一个简单示例。在这个例子中,我们将模拟一个天气预报系统,其中WeatherData充当被观察者(Subject),负责收集气象数据并通知观察者(Observer)——在这里是具体的显示设备,如CurrentConditionsDisplay

        1. 创建观察者接口

        首先,定义一个观察者接口,声明更新方法。

import java.util.EventObject;// 观察者接口
interface Observer {void update(EventObject event);
}

2. 定义被观察者接口与具体被观察者

        接下来,定义被观察者接口,包含注册、删除观察者以及通知观察者的方法。同时,实现具体的被观察者类WeatherData

import java.util.ArrayList;
import java.util.List;// 被观察者接口
interface Observable {void addObserver(Observer o);void deleteObserver(Observer o);void notifyObservers();
}// 具体被观察者 - 天气数据
class WeatherData implements Observable {private List<Observer> observers;private float temperature;private float humidity;private float pressure;public WeatherData() {this.observers = new ArrayList<>();}public void measurementsChanged() {notifyObservers();}@Overridepublic void addObserver(Observer o) {observers.add(o);}@Overridepublic void deleteObserver(Observer o) {observers.remove(o);}@Overridepublic void notifyObservers() {for (Observer observer : observers) {observer.update(new WeatherEvent(this, temperature, humidity, pressure));}}// 其他方法略,如setMeasurements等用于更新数据
}

3. 创建事件对象

        定义一个事件对象,用于传递给观察者。

// 事件对象
class WeatherEvent extends EventObject {private float temperature;private float humidity;private float pressure;public WeatherEvent(Object source, float temperature, float humidity, float pressure) {super(source);this.temperature = temperature;this.humidity = humidity;this.pressure = pressure;}public float getTemperature() {return temperature;}public float getHumidity() {return humidity;}public float getPressure() {return pressure;}
}

4. 实现具体观察者

        定义具体的观察者类,比如显示当前天气状况的显示器。

// 具体观察者 - 显示当前天气状况
class CurrentConditionsDisplay implements Observer {private float temperature;private float humidity;@Overridepublic void update(EventObject event) {if (event instanceof WeatherEvent) {WeatherEvent weatherEvent = (WeatherEvent) event;this.temperature = weatherEvent.getTemperature();this.humidity = weatherEvent.getHumidity();display();}}public void display() {System.out.println("Current conditions: " + temperature + "F degrees and " + humidity + "% humidity");}
}

5. 客户端代码

        最后,客户端代码创建被观察者和观察者实例,并模拟数据更新过程。

public class ObserverPatternDemo {public static void main(String[] args) {WeatherData weatherData = new WeatherData();CurrentConditionsDisplay currentDisplay = new CurrentConditionsDisplay();weatherData.addObserver(currentDisplay);// 模拟气象数据变化weatherData.setMeasurements(80, 65, 30.4f); // 假设这是更新数据的方法}
}

        请注意,为了简洁起见,示例中省略了某些方法的实现细节,如setMeasurements方法,实际应用中应确保在数据更新时调用measurementsChanged方法来通知观察者。

相关文章:

设计模式:观察者模式

观察者模式&#xff08;Observer Pattern&#xff09;是一种行为设计模式&#xff0c;它定义了对象之间的一对多依赖关系&#xff0c;当一个对象的状态发生改变时&#xff0c;所有依赖于它的对象都会得到通知并被自动更新。这种模式通常被用来实现事件处理系统、实时数据更新、…...

ICode国际青少年编程竞赛- Python-5级训练场-带参数函数

ICode国际青少年编程竞赛- Python-5级训练场-带参数函数 1、 def get_item(a):Dev.step(a)Dev.step(-a) get_item(4) Spaceship.step(2) get_item(2) Spaceship.step(3) get_item(5) Spaceship.step(2) get_item(3) Spaceship.step(3) get_item(4)2、 def get_item(a): D…...

运维别卷系列 - 云原生监控平台 之 02.prometheus exporter 实践

文章目录 [toc]exporter 简介常用的 exporternode-exporter 实践创建 svc创建 daemonsetprometheus 配置服务发现 exporter 简介 随着 Prometheus 的流行&#xff0c;很多系统都已经自带了用于 Prometheus 监控的接口&#xff0c;例如 etcd、Kubernetes、CoreDNS 等&#xff0c…...

OSPF基本配置

1.启动OSPF进程 [rijospf1 router-id 1.1.1.1 --- 手工配置RID [r1-ospf-1) 2&#xff0c;创建区域 [r1-ospf-1]area 0 [r1-ospf-1-area-0.0.0.0) 3&#xff0c;宣告 目的:1&#xff0c;只有被宣告网段中的接口才能被激活。 --- 激活接口 ---- 只有激活的接口才能收发OSPF的…...

HIVE大数据平台SQL优化分享

相信很多小伙伴在面试的时候&#xff0c;必然跳不过去的一个问题就是SQL脚本的优化&#xff0c;这是很多面试官爱问的问题&#xff0c;也是可以证明你实力进阶的一个重要的能力。 下面给大家分享一个重量级的大数据行业sql技能---hive大数据平台SQL优化。 此文章是大数据平台…...

JS算法-十大排序算法(上)

思想小剧场 如果我的相对论被证明是正确的&#xff0c;德国人就会说我是德国人&#xff0c;法国人会说我是一个世界公民&#xff1b;如果我的相对论被否定了&#xff0c;法国佬就会骂我是德国鬼子&#xff0c;而德国人就会把我归为犹太人。—爱因斯坦 以下案例都是升序 const a…...

c++编程(11)——string类的模拟实现

欢迎来到博主的专栏——c编程 博主ID&#xff1a;代码小豪 文章目录 前言string类的模拟实现string的成员对象构造、赋值、析构访问成员对象的接口访问字符串中的元素迭代器对字符序列的插入、删除元素操作mystring类的相关操作 mystring类的所有模拟实现以及测试案例 前言 本…...

Python从0到POC编写--函数

数学函数&#xff1a; 1. len len() 函数返回对象&#xff08;字符、列表、元组等&#xff09;长度或项目个数&#xff0c; 例如&#xff1a; str "python" len(str)2. range range() 函数返回的是一个可迭代对象&#xff08;类型是对象&#xff09;&#xff0c;…...

【教程】Linux/Jetson 安装X11VNC同步屏幕内容

转载请注明出处&#xff1a;小锋学长生活大爆炸[xfxuezhagn.cn] 如果本文帮助到了你&#xff0c;请不吝给个[点赞、收藏、关注]哦~ 目录 背景说明 实际效果 安装步骤 安装 x11vnc 配置 x11vnc 配置 x11vnc 作为系统服务 使用 VNC 客户端连接 背景说明 通常vnc-server是单…...

【LLM第五篇】名词解释:prompt

1.是什么 提示工程&#xff08;Prompt Engineering&#xff09;是一门较新的学科&#xff0c;关注提示词开发和优化&#xff0c;帮助用户将大语言模型&#xff08;Large Language Model, LLM&#xff09;用于各场景和研究领域。 掌握了提示工程相关技能将有助于用户更好地了解…...

k8s v1.20二进制部署 部署 CNI 网络组件 部署 Calico

一、部署 flannel 1.1.K8S 中 Pod 网络通信 ●Pod 内容器与容器之间的通信 在同一个 Pod 内的容器&#xff08;Pod 内的容器是不会跨宿主机的&#xff09;共享同一个网络命名空间&#xff0c;相当于它们在同一台机器上一样&#xff0c;可以用 localhost 地址访问彼此的端口。…...

在React中利用Postman测试代码获取数据

文章目录 概要名词解释1、Postman2、axios 使用Postman测试API在React中获取并展示数据小结 概要 在Web开发中&#xff0c;通过API获取数据是一项常见任务。Postman是一个功能强大的工具&#xff0c;可以帮助开发者测试API&#xff0c;并查看API的响应数据。在本篇博客中&…...

嵌入式学习-通用定时器

简介 框图介绍 时钟选择 计数器部分 输入捕获和输出比较框图 嵌入式学习全文参考&#xff08;小向是个der&#xff09;做笔记&#xff1a;https://blog.csdn.net/qq_41954556/article/details/129735708...

培训行业有哪些ai工具?

培训行业利用人工智能&#xff08;AI&#xff09;工具的方式多种多样&#xff0c;其中一些常见的工具包括&#xff1a; 1. **经AI深度学习的OCR软件**&#xff1a;OCR能给培训行业带来很大的便利&#xff0c;能大大提高工作效率和降低文字录入的成本&#xff0c;但一般的OCR工具…...

7.STL中string的一些超常用函数 (附习题)

目录 1.find 2.atoi 3.to_string 4.getline 【leetcode 习题】 387.字符串中的第一个唯一字符 125. 验证回文串 1.find 1.查找第一次出现的目标字符串&#xff1a;说明&#xff1a;如果查找成功则输出查找到的第一个位置&#xff0c;否则返回-1&#xff1b; s1.find(s2…...

GPT搜索鸽了!改升级GPT-4

最近OpenAI太反常&#xff0c;消息一会一变&#xff0c;直让人摸不着头脑。 奥特曼最新宣布&#xff1a;5月13日开发布会&#xff0c;不是GPT-5&#xff0c;也不是盛传的GPT搜索引擎&#xff0c;改成对ChatGP和GPT-4的升级&#xff5e; 消息一出&#xff0c;大伙儿都蒙了。 之…...

数字绘画教学实训解决方案

一、建设背景 1.1政策背景 教育信息化政策推动&#xff1a;近年来&#xff0c;随着教育信息化政策的不断推动&#xff0c;各级教育部门纷纷出台相关政策&#xff0c;鼓励和支持教育信息化的发展。数字绘画作为现代艺术教育的重要组成部分&#xff0c;其教学实训解决方案的建设…...

C#之如何判断数据类型

一、GetType方法 a.GetType()&#xff1a;获取当前变量的类型对象 string str "Hello World";Console.WriteLine(str.GetType()); 结果: 二、typeof方法 typeof(Int)&#xff1a;获取的是Int类型的类型对象 int num 10;Console.WriteLine(num.GetType() typeof(i…...

算法学习笔记(Tarjan)

本文介绍 T a r j a n Tarjan Tarjan求强联通分量、找割点和割边、找环。 Tarjan求强联通分量 例题&#xff1a;【模板】有向图缩点 题目描述 给定一个 n n n点 m m m边的有向图&#xff08;保证不存在重边与自环&#xff0c;但不保证连通&#xff09;&#xff0c;请你求出…...

一台linux通过另一台linux访问互联网-TinyProxy

参考&#xff1a; https://blog.csdn.net/weixin_41831919/article/details/113061317https://www.yuncongz.com/archives/1.htmlhttps://blog.csdn.net/aoc68397/article/details/101893369 环境&#xff1a;ubuntu 18.04 机器1: IP 219.216.65.252 (可以访问外网) 机器2: IP…...

stm32G473的flash模式是单bank还是双bank?

今天突然有人stm32G473的flash模式是单bank还是双bank&#xff1f;由于时间太久&#xff0c;我真忘记了。搜搜发现&#xff0c;还真有人和我一样。见下面的链接&#xff1a;https://shequ.stmicroelectronics.cn/forum.php?modviewthread&tid644563 根据STM32G4系列参考手…...

在HarmonyOS ArkTS ArkUI-X 5.0及以上版本中,手势开发全攻略:

在 HarmonyOS 应用开发中&#xff0c;手势交互是连接用户与设备的核心纽带。ArkTS 框架提供了丰富的手势处理能力&#xff0c;既支持点击、长按、拖拽等基础单一手势的精细控制&#xff0c;也能通过多种绑定策略解决父子组件的手势竞争问题。本文将结合官方开发文档&#xff0c…...

srs linux

下载编译运行 git clone https:///ossrs/srs.git ./configure --h265on make 编译完成后即可启动SRS # 启动 ./objs/srs -c conf/srs.conf # 查看日志 tail -n 30 -f ./objs/srs.log 开放端口 默认RTMP接收推流端口是1935&#xff0c;SRS管理页面端口是8080&#xff0c;可…...

华为OD机试-食堂供餐-二分法

import java.util.Arrays; import java.util.Scanner;public class DemoTest3 {public static void main(String[] args) {Scanner in new Scanner(System.in);// 注意 hasNext 和 hasNextLine 的区别while (in.hasNextLine()) { // 注意 while 处理多个 caseint a in.nextIn…...

spring:实例工厂方法获取bean

spring处理使用静态工厂方法获取bean实例&#xff0c;也可以通过实例工厂方法获取bean实例。 实例工厂方法步骤如下&#xff1a; 定义实例工厂类&#xff08;Java代码&#xff09;&#xff0c;定义实例工厂&#xff08;xml&#xff09;&#xff0c;定义调用实例工厂&#xff…...

linux 下常用变更-8

1、删除普通用户 查询用户初始UID和GIDls -l /home/ ###家目录中查看UID cat /etc/group ###此文件查看GID删除用户1.编辑文件 /etc/passwd 找到对应的行&#xff0c;YW343:x:0:0::/home/YW343:/bin/bash 2.将标红的位置修改为用户对应初始UID和GID&#xff1a; YW3…...

微服务商城-商品微服务

数据表 CREATE TABLE product (id bigint(20) UNSIGNED NOT NULL AUTO_INCREMENT COMMENT 商品id,cateid smallint(6) UNSIGNED NOT NULL DEFAULT 0 COMMENT 类别Id,name varchar(100) NOT NULL DEFAULT COMMENT 商品名称,subtitle varchar(200) NOT NULL DEFAULT COMMENT 商…...

Robots.txt 文件

什么是robots.txt&#xff1f; robots.txt 是一个位于网站根目录下的文本文件&#xff08;如&#xff1a;https://example.com/robots.txt&#xff09;&#xff0c;它用于指导网络爬虫&#xff08;如搜索引擎的蜘蛛程序&#xff09;如何抓取该网站的内容。这个文件遵循 Robots…...

C++ 求圆面积的程序(Program to find area of a circle)

给定半径r&#xff0c;求圆的面积。圆的面积应精确到小数点后5位。 例子&#xff1a; 输入&#xff1a;r 5 输出&#xff1a;78.53982 解释&#xff1a;由于面积 PI * r * r 3.14159265358979323846 * 5 * 5 78.53982&#xff0c;因为我们只保留小数点后 5 位数字。 输…...

Golang——6、指针和结构体

指针和结构体 1、指针1.1、指针地址和指针类型1.2、指针取值1.3、new和make 2、结构体2.1、type关键字的使用2.2、结构体的定义和初始化2.3、结构体方法和接收者2.4、给任意类型添加方法2.5、结构体的匿名字段2.6、嵌套结构体2.7、嵌套匿名结构体2.8、结构体的继承 3、结构体与…...