备忘录模式
理论
备忘录(Memento)模式,在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态。这样以后就可将该对象恢复到原先保存的状态。

备忘录模式应用场景:
1. 比较适用于功能比较复杂,但需要维护或记录属性历史的类,或者需要保存的属性只是众多属性中的一小部分,Originator 可以根据保存的 Memento 信息还原到前一状态。
2. 当角色的状态改变的时候,有可能这个状态无效,这时候可以使用暂时存储起来的备忘录将状态复原。
实例
模拟游戏场景,一个游戏角色有生命力、攻击力、防御力等数据,在打Boss前后会不一样,我们允许玩家与Boss决斗的结果不理想时可以让游戏恢复到决斗前
UML类图

代码实现
#include <iostream>
using namespace std;
//游戏状态存储箱类
class RoleStateMemento {
public:
RoleStateMemento(int _vit, int _atk, int _def) :vit(_vit), atk(_atk), def(_def) {}
int GetVit() { return vit; }
int GetAtk() { return atk; }
int GetDef() { return def; }
private:
int vit;
int atk;
int def;
};
//发起人(Originator)类
class Originator {
public:
//初始化状态
void SetState() {
vit = 100;
atk = 100;
def = 100;
}
//战斗后状态
void Battle() {
vit = 0;
atk = 0;
def = 0;
}
//保存当前状态到备忘录
RoleStateMemento* SaveState() { return new RoleStateMemento(vit, atk, def); }
//恢复备忘录
void RecoveryState(RoleStateMemento* memento){
this->vit = memento->GetVit();
this->atk = memento->GetAtk();
this->def = memento->GetDef();
}
//显示当前状态
void Display() {
cout << "当前状态: " << endl;
cout << "生命力: " << vit << " ";
cout << "攻击力: " << atk << " ";
cout << "防御力: " << def << " ";
cout << endl;
}
private:
int vit; //生命力
int atk; //攻击力
int def; //防御力
};
//角色状态管理类
class RoleStateCaretaker {
public:
void SetMemento(RoleStateMemento* memento) { Memento = memento; }
RoleStateMemento* GetMemento() { return Memento; }
private:
RoleStateMemento* Memento;
};
//客户端代码
int main()
{
//战斗前
Originator role;
role.SetState();
role.Display();
//保存当前进度
RoleStateCaretaker CreateMemento;
CreateMemento.SetMemento(role.SaveState());
//战斗后
role.Battle();
role.Display();
//恢复备忘录
role.RecoveryState(CreateMemento.GetMemento());
role.Display();
system("pause");
return 0;
}
运行结果

好处:把要保存的细节给封装在了 Memento 中了,如果要更改保存的细节不会影响客户端。

浙公网安备 33010602011771号