一、什么是备忘录模式
备忘录模式是一种行为型设计模式,它允许在不破坏封装性的前提下捕获一个对象的内部状态,并在该对象之外保存这个状态,以便在需要时可以将对象恢复到原先保存的状态。
二、备忘录模式的实现原理
- 发起人(Originator):发起人是需要被保存状态的对象。它包含了需要保存的状态,并能够创建备忘录对象和从备忘录对象中恢复状态。发起人可以通过提供获取当前状态和设置当前状态的方法来实现状态的保存和恢复。
- 备忘录(Memento):备忘录是用于存储发起人对象状态的对象。它通常包含了发起人对象的部分或全部状态信息。备忘录对象应该提供获取和设置状态的方法,但是只能由发起人对象访问。
- 管理者(Caretaker):管理者负责保存和恢复备忘录对象。它可以保存多个备忘录对象,并提供获取和设置备忘录对象的方法。管理者可以根据需要选择性地保存和恢复备忘录对象。
三、备忘录模式的应用场景
- 撤销操作:备忘录模式可以用于实现撤销操作,当用户执行某个操作后,可以将当前对象的状态保存到备忘录中,当用户需要撤销操作时,可以从备忘录中恢复对象的状态。
- 数据库事务回滚:在数据库操作中,备忘录模式可以用于实现事务的回滚功能。当执行数据库操作时,可以将数据库的状态保存到备忘录中,如果操作失败或需要回滚时,可以从备忘录中恢复数据库的状态。
- 游戏存档:备忘录模式可以用于游戏中的存档功能。当玩家需要保存当前游戏进度时,可以将游戏状态保存到备忘录中,当玩家需要继续游戏时,可以从备忘录中恢复游戏状态。
- 播放器状态保存:备忘录模式可以用于保存播放器的状态。当用户暂停或停止播放时,可以将播放器的状态保存到备忘录中,当用户需要继续播放时,可以从备忘录中恢复播放器的状态。
四、备忘录模式的代码实现
//+------------------------------------------------------------------+
//| structure |
//+------------------------------------------------------------------+
// | Originator |- - ->| Memento |<-------o|Caretaker|
// |--------------------------| |----------|
// |SetMemento(Memento m) | |GetState()|
// | state=m.GetState() | |SetState()|
// |CreateMemento() | |----------|
// | return new Memento(state)| |state |
// |--------------------------|
// |state |
//+------------------------------------------------------------------+
// memento pattern participant
class Memento
{
protected:
string m_state;
public:
string GetState(void);
void SetState(string);
Memento(string);
};
//+------------------------------------------------------------------+
//| constructor |
//+------------------------------------------------------------------+
Memento::Memento(string state): m_state(state)
{
}
//
string Memento::GetState(void)
{
return m_state;
}
//
void Memento::SetState(string state)
{
m_state=state;
}
//
class Caretaker
{
public:
Memento* memento;
~Caretaker(void);
};
//
Caretaker::~Caretaker(void)
{
if(CheckPointer(memento)==1)
{
delete memento;
}
}
//
class Originator
{
protected:
string m_state;
public:
void SetMemento(Memento& memento);
Memento* CreateMemento(void);
string State(void);
void State(string);
};
//
void Originator::SetMemento(Memento& memento)
{
m_state=memento.GetState();
printf("restoring originator state from memento to %s",m_state);
}
//
Memento* Originator::CreateMemento(void)
{
printf("creating memento with current state %s",m_state);
return new Memento(m_state);
}
//
void Originator::State(string state)
{
printf("changing originator state to %s",state);
m_state=state;
}
//
string Originator::State(void)
{
return m_state;
}
//
void OnStart()
{
Originator originator;
Caretaker caretaker;
//---
originator.State("on");
caretaker.memento=originator.CreateMemento();
originator.State("off");
originator.SetMemento(caretaker.memento);
}
//+------------------------------------------------------------------+
//| output |
//+------------------------------------------------------------------+
// changing originator state to on
// creating memento with current state on
// changing originator state to off
// restoring originator state from memento to on