备忘录模式(Memento Pattern)
目的意图
备忘录模式是一种行为设计模式,目的是在不破坏封装性的前提下,捕获并保存一个对象的内部状态,以便在之后可以将对象恢复到这个状态。备忘录模式的核心思想是将对象的状态保存到外部,这样对象可以在不暴露其内部结构的情况下被恢复。
关键角色
-
Originator(发起人):
- 这是需要保存和恢复状态的对象。
- 它创建一个备忘录(Memento)对象来存储其内部状态。
- 它可以从备忘录中恢复其状态。
-
Memento(备忘录):
- 这是存储 Originator 内部状态的对象。
- 它通常是不可变对象,防止状态被意外修改。
-
Caretaker(管理者):
- 这是负责保存和恢复备忘录的对象。
- 它不直接操作备忘录的内部状态,而是通过 Originator 来管理备忘录。
适用场合
备忘录模式适用于以下场景:
-
需要保存对象的内部状态:
- 当需要保存对象的内部状态,并在之后恢复到该状态时,备忘录模式非常有用。例如,文本编辑器中的撤销/重做功能。
-
不希望破坏对象的封装性:
- 如果直接访问对象的内部状态会导致封装性被破坏,备忘录模式可以通过封装状态保存和恢复逻辑来避免这种情况。
-
需要管理多个状态快照:
- 当需要保存多个状态快照,以便在不同时间点恢复对象时,备忘录模式可以很好地管理这些快照。例如,游戏中的存档功能。
-
状态恢复操作具有复杂性:
- 当状态恢复操作比较复杂,涉及到多个对象或多个状态时,备忘录模式可以将这些复杂的操作封装在 Originator 中,简化客户端代码。
示例代码
以下是一个简单的 C++ 示例,演示如何使用备忘录模式来实现文本编辑器的撤销功能。
#include <iostream>
#include <string>
#include <vector>
// Memento: 存储 Originator 的状态
class Memento {
public:
Memento(const std::string& state) : state(state) {}
std::string getState() const {
return state;
}
private:
std::string state;
};
// Originator: 需要保存和恢复状态的对象
class TextEditor {
public:
void setText(const std::string& text) {
this->text = text;
std::cout << "Text set to: " << text << std::endl;
}
std::string getText() const {
return text;
}
Memento save() const {
return Memento(text);
}
void restore(const Memento& memento) {
text = memento.getState();
std::cout << "Restored to text: " << text << std::endl;
}
private:
std::string text;
};
// Caretaker: 管理 Memento 对象
class History {
public:
void push(const Memento& memento) {
history.push_back(memento);
}
Memento pop() {
if (history.empty()) {
throw std::runtime_error("No mo