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

Java 编程之备忘录模式

前言

有时候,我们真希望人生能有“Ctrl+Z”。在日常生活中,我们经常使用“撤销”功能,例如在写 Word、画图、写代码时一不小心操作失误,就希望能回到之前的状态。这种**“状态快照 + 恢复”**机制,在设计模式中就叫做:备忘录模式(Memento Pattern)

本文将通过一个现实场景——写小说与撤销编辑操作,来贯穿讲解备忘录模式,并用 Java 代码实现一套完整的例子,让你在概念与实践中都收获满满。

一、备忘录模式是什么

定义:在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态,以便以后将其恢复。

换句话说,它是实现“撤销(Undo)”、“回退(Rollback)”、“恢复(Recover)”的核心设计模式。

二、小说家与“撤销按钮”

想象你是个小说作者,每天都在写小说的草稿。

  • 每写一段内容,你都可以“保存一下”(打个草稿快照);
  • 写崩了?你就点击“撤销”,恢复之前保存的状态;
  • 每一个“保存”其实就是一个备忘录对象(Memento)
  • 你就是“发起者(Originator)”;
  • 草稿箱(Caretaker)里存着所有的“保存记录”。

三、核心结构类比

角色名类比于现实作用说明
Originator小说作者拥有真实内容和状态,可以保存或恢复
Memento每一段草稿状态快照,保存了当前文本
Caretaker草稿箱保存多个草稿,但不关心内容细节

四、Java 实例

如下以java来实现:小说草稿的撤销与恢复

Memento:草稿快照

// 草稿状态(备忘录)
public class DraftMemento {private final String content;public DraftMemento(String content) {this.content = content;}public String getContent() {return content;}
}

Originator:小说作者

// 发起者,写小说的作者
public class Author {private String content;public void write(String text) {this.content = text;System.out.println("🖊️ 当前写作内容:" + content);}public DraftMemento saveDraft() {System.out.println("📁 保存草稿");return new DraftMemento(content);}public void restoreDraft(DraftMemento memento) {this.content = memento.getContent();System.out.println("↩️ 恢复到草稿:" + content);}public String getContent() {return content;}
}

Caretaker:草稿箱

import java.util.Stack;// 草稿箱,负责保存多个版本
public class DraftCaretaker {private final Stack<DraftMemento> drafts = new Stack<>();public void save(DraftMemento draft) {drafts.push(draft);}public DraftMemento undo() {if (!drafts.isEmpty()) {return drafts.pop();}return null;}public boolean hasHistory() {return !drafts.isEmpty();}
}

测试主类:模拟写作与撤销

public class MementoDemo {public static void main(String[] args) {Author author = new Author();DraftCaretaker caretaker = new DraftCaretaker();author.write("故事的开始:从前有座山");caretaker.save(author.saveDraft());author.write("故事第二章:山里有个庙");caretaker.save(author.saveDraft());author.write("故事第三章:庙里住着老和尚和小和尚");System.out.println("\n⚠️ 写崩了!撤销!");if (caretaker.hasHistory()) {author.restoreDraft(caretaker.undo());  // 撤销到第二章}System.out.println("\n📄 当前内容:" + author.getContent());}
}

输出示例

🖊️ 当前写作内容:故事的开始:从前有座山
📁 保存草稿
🖊️ 当前写作内容:故事第二章:山里有个庙
📁 保存草稿
🖊️ 当前写作内容:故事第三章:庙里住着老和尚和小和尚⚠️ 写崩了!撤销!
↩️ 恢复到草稿:故事第二章:山里有个庙📄 当前内容:故事第二章:山里有个庙

五、UML图

在这里插入图片描述

@startuml
title 备忘录模式(Memento Pattern)UML 类图class Author {- content: String+ write(text: String): void+ saveDraft(): DraftMemento+ restoreDraft(memento: DraftMemento): void+ getContent(): String
}class DraftMemento {- content: String+ getContent(): String
}class DraftCaretaker {- drafts: Stack<DraftMemento>+ save(m: DraftMemento): void+ undo(): DraftMemento+ hasHistory(): boolean
}Author --> DraftMemento : 创建备份
DraftCaretaker --> DraftMemento : 保存 & 提取
Author --> DraftCaretaker : 恢复状态

六、适用场景一览

场景描述
编辑器的撤销重做文本编辑、画图软件
游戏存档系统保存玩家状态,失败后恢复
数据库事务回滚恢复操作前的状态
配置修改回滚系统设置、软件参数

七、小结

优点:

  • 不破坏封装性,内部状态对外透明
  • 实现撤销/恢复简单灵活
  • 多状态历史管理方便

注意事项:

  • 每次保存都会占用内存,可能引起性能开销
  • 状态对象较大时,建议存储增量而非全量

备忘录模式就像我们生活中的“后悔药”,
它帮你把时间打包,瓶中封印,
等你想“回到昨天”,只需轻轻一唤。

八、参考

《23种设计模式概览》
在这里插入图片描述

相关文章:

  • SQL学习笔记3
  • LeetCode--37.解数独
  • 使用 Nordic Connect SDK (NCS) 而不是标准 Zephyr 的优势是什么
  • AI+时代已至|AI人才到底该如何培育?
  • ubuntu部署woodpecker依赖gitea
  • 6月26日星期四今日早报简报微语报早读
  • [论文阅读]RaFe: Ranking Feedback Improves Query Rewriting for RAG
  • GraphQL注入 -- GPN CTF 2025 Real Christmas
  • 通过对 NIDS 自适应黑盒对抗性攻击披露漏洞
  • 攻防世界-MISC-4-2
  • 力扣网C语言编程题:搜索插入位置
  • Python 数据分析与可视化 Day 8 - Pandas 高级操作技巧
  • 表单数据收集实现分析
  • Python 中 `bytes` 与 `str` 的核心差异及注意事项
  • python中学物理实验模拟:斜面受力分析
  • IDEA + Spring Boot + javadoc 实例应用
  • Java底层原理:深入理解JVM性能调优与监控
  • 腾讯云产品都有哪些
  • 永磁无刷电机旋转原理
  • 大脑感官:视觉系统中将感观信息转换为神经信号