定义
在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态,这样以后就可将该对象恢复到原先保存的状态。
案例
比如现在有一个绘图系统,我们在Viewer里面画了一些图形,但是在绘制的过程中可能画出的图像不是想要的,这时候需要到正确的绘制状态,这时候可以在每次绘制的时候保存绘制的状态信息,但是要在不改变Viewer的封装性的前提下实现,有点困难,这时候就可以使用备忘录模式。
一个备忘录Memento是一个对象,它存储另一个对象在某个瞬间的内部状态,后者称为备忘录的原发器(originator):
Memento类是用来保存Viewer的相关状态:
class Memento
{
public:
void setState(State* state) { m_state = state; }
State* state() const { return m_state; }
private:
friend class Viewer;
Memento() { }
private:
State* m_state;
};
Viewer是Memento的友元类,可以在需要的时刻创建Memento对象,来保存自身的状态信息:
class Viewer
{
public:
void drawGraphics();
Memento* createMemento();
void setMemento(Memento* memento);
};
Memento* Viewer::createMemento()
{
State* state = getSelfState();
Memento* memento = new Memento();
memento->setState(state);
return memento;
}
void setMemento(Memento* memento)
{
setSelfState(memento->state());
}
Command类是用来绘制图形,并可以回滚操作:
class Command
{
public:
void execute();
void unExecute();
private:
Viewer* m_viewer;
std::vector<Memento*> m_mementos;
};
void Command::execute()
{
m_viewer->drawGraphics();
m_mementos.push_back(m_viewer->createMemento());
}
void Command::unExecute()
{
if(!m_memento.isEmpty())
{
m_viewer->setMemento(m_mementos.back());
m_mementso.pop_back();
}
}
效果
- 保持封装,避免了暴露由自身管理但必须存储在自身之外的数据
- 简化了原发器Viewer,把管理存储状态信息的重任交给了Memento
- 使用代价高,可能由于频繁的操作创建了大量的Memento,可以通过顺序存储,下一次只存储上一次保存后改变的信息