备忘录模式

面临问题:

对象状态的变化无端,如何回溯恢复对象在某个点的状态?

在软件构建过程中,某些对象的状态在转换过程中,可能由于某种需要,要求程序能够回溯到对象之前处于某个点时的状态。如果使用一些公用接口来让其他对象得到对象的状态,便会暴露对象的细节实现。如何实现对象状态的良好保存与恢复?但同时又不会因此而破坏对象本身的封装性?


解决方案:

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

一个memento是一个对象, 它存储另一个对象在某个瞬间的内部状态,而后者称为备忘录的原发器(originator)。当需要设置原发器的检查点(checkpoint)时, 取消操作机制会向原发器请求一个备忘录。原发器用描述当前状态的信息初始化该备忘录。只有原发器可以向备忘录中存取信息备忘录对其他的对象“不可见”

也就是说,备忘录对除了原发器之外的对象都不可见。只有原发器,也就是拥有状态的对象,可以对备忘录进行操作。如果有取消操作,只要向这个对象请求一个备忘录就可以了。


备忘录是一个行为型模式,状态是不断变化的,这个和状态模式的不同的是,客户的意图是干什么?客户只想恢复对象之前的状态,而状态模式是,随着状态的改变会产生不同的行为。一个行为是保存上一次的状态,能够实现undo操作。(虽然命令模式也能实现undo操作,其实他是降一个命令封装了一系列操作,这个undo操作是写死的,而备忘录比较活)。状态模式是根据不同的状态,让其产生不同的行为。虽然都涉及状态,但是两者本意是不一样的。(个人理解)



个人感觉备忘录类中少了一个指向原发器的虚箭头。一个依赖关系。因为备忘录的构造函数需要用到原发器对象,以便于原发器对象的状态能够传给备忘录对象。



 Memento(备忘录)
 备忘录存储原发器对象的内部状态。原发器根据需要决定备忘录存储原发器的哪些内部状态。 防止原发器以外的其他对象访问备忘录。备忘录实际上有两个接口,管理者(caretaker) 只能看到备忘录的窄接口—它只能将备忘录传递给其他对象。相反, 原发器能够看到一个宽接口, 允许它访问返回到先前状态所需的所有数据。理想的情况是只允许生成本备忘录的那个原发器访问本备忘录的内部状态。
 Originator(原发器)
原发器创建一个备忘录,用以记录当前时刻它的内部状态。 使用备忘录恢复内部状态。
 Caretaker(管理器)
负责保存好备忘录。 不能对备忘录的内容进行操作或检查。


管理器向原发器请求一个备忘录, 保留一段时间后,将其送回给原发器

Caretaker care;

Memento mem;

Originator ori;

State  state;

ori.setState() 先对原发器设置一个状态,然后ori.createMem()创建一个备忘录对象。得到一个备忘录对象,再调用care中的,setMem设置管理器的备忘录。

如果想恢复备忘录中存储的原发器的状态,通过对管理器的getMem,获得备忘录对象,这时候调用 ori.restoreMemento。就会成功的将备忘录的存储的状态,传给原发器。这样,就能恢复之前的状态。(个人写的有点混乱)。不过自己是能理解了。



应用实例:

某游戏为了给玩家提供更好的用户体验,在游戏过程中设臵一个恢复点,记录当前游戏场景,如果玩家想返回到先前场景,可从所设恢复点开始重新游戏。


相关模式:

Command:命令可使用备忘录来为可撤销的操作维护状态
Iterator:当备忘录模式支持多个checkpoints时,在各个checkpoints之间进行遍历可用迭代模式


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值