备忘录模式
字数: 0 字 时长: 0 分钟
简介
备忘录模式(Memento Pattern)核心思想是:在不破坏对象封装性的前提下,捕获一个对象的内部状态,并在将来需要的时候能恢复这个状态。优点是支持撤销和回退操作,封装性强;缺点是内存开销大、恢复状态时有限制,不支持更灵活的版本控制。
UML 类图
- 发起人(Originator):需要保存状态的对象,负责创建和恢复备忘录
- 备忘录(Memento):存储发起人的内部状态,是一个纯数据对象
- 管理者(Caretaker):负责保存备忘录对象,但不直接操作备忘录的内容
实现示例
以“文档编辑器撤销/重做”为例:
java
// 1. 创建备忘录对象
class DocumentMemento {
private String content;
public DocumentMemento(String content) {
this.content = content;
}
// 只提供读取功能,确保封装性
public String getContent() {
return content;
}
}
// 2. 创建发起人(要保存状态的文档)
class Document {
@Getter
@Setter
private String content;
public Document(String content) {
this.content = content;
}
public DocumentMemento save() {
return new DocumentMemento(this.content); // 备份
}
public void restore(DocumentMemento memento) {
this.content = memento.getContent(); // 重做
}
}
// 3. 创建管理者 (负责保存多个状态,用于撤销和重做)
class History {
private Stack<DocumentMemento> history = new Stack<>();
private Stack<DocumentMemento> redoStack = new Stack<>();
public void pushMemento(DocumentMemento memento) {
history.push(memento);
redoStack.clear(); // 每次新操作时清空重做栈
}
public DocumentMemento popMemento() {
if (!history.isEmpty()) {
DocumentMemento memento = history.pop();
redoStack.push(memento);
return memento;
}
return null;
}
public DoccumentMemento popRedoMemento() {
if (!redoStack.isEmpty()) {
DocumentMemento memento = redoStack.pop();
history.push(memento);
return memento;
}
return null;
}
}
// 4. 调用示例
public static void main(String[] args) {
Document document = new Document("初始内容");
History history = new History();
// 保存初始状态
history.pushMemento(document.save());
// 修改文档内容,保存状态
document.setContent("第一次修改后的内容");
history.pushMemento(document.save());
// 第二次修改
document.setContent("第二次修改后的内容");
history.pushMemento(document.save());
// 撤销 (回到第一次修改后的状态)
document.restore(history.popMemento());
// 再次撤销 (回到初始状态)
document.restore(history.popMemento());
// 重做 (回到第一次修改后的状态)
document.restore(history.popRedoMemento());
}