定义:
备忘录模式又叫快照模式,是指在不违背封装原则的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态,以便之后恢复对象为先前的状态。备忘录模式的特点就是保存之前的状态,并且恢复。生活中没有后悔药,但是代码的中却存在后悔药。
实现:
在备忘录模式中存在三个基本的角色,发起人,备忘录角色,备忘录管理员
- Originator发起人角色
记录当前时刻的内部状态,负责定义哪些属于备份范围的状态,负责创建和恢复备忘录数据。
- Memento备忘录角色
负责存储Originator发起人对象的内部状态,在需要的时候提供发起人需要的内部状态。
- Caretaker备忘录管理员角色
对备忘录进行管理、保存和提供备忘录。
代码:
package com.memento;
/**
* 备忘录角色
*/
public class Memento {
//发起人的内部状态
private String status = "";
public Memento(String _status){
this.status = _status;
}
//获取状态
public String getStatus() {
return status;
}
//设置状态
public void setStatus(String status) {
this.status = status;
}
}
package com.memento;
/**
*备忘录管理者
*
*/
public class Caretaker {
private Memento memento;
public Memento getMemento(){
return memento;
}
public void setMemento(Memento memento) {
this.memento = memento;
}
}
package com.memento;
/**
* 发起人文图
*/
public class Originator {
//内部状态
private String status = "";
public String getStatus() {
return status;
}
public void setStatus(String status) {
this.status = status;
}
//创建一个备忘录
public Memento createMemento(){
return new Memento(this.status);
}
//回复一个备忘录
public void restoreMemento(Memento memento){
this.setStatus(memento.getStatus());
}
}
package com.memento;
/**
* 备忘录模式
*/
public class Client {
public static void main(String[] args) {
//定义一个发起人
Originator originator = new Originator();
originator.setStatus("1");
System.out.println("status: "+originator.getStatus());
//定义一个备忘录管理员
Caretaker caretaker = new Caretaker();
//创建一个备忘录
caretaker.setMemento(originator.createMemento());
originator.setStatus("2");
System.out.println("status: "+originator.getStatus());
originator.restoreMemento(caretaker.getMemento());
System.out.println("status: "+originator.getStatus());
}
}
//打印结果
status: 1
status: 2
status: 1
运行代码后,发起人 Originator在初始的状态设置为1,然后将状态保存,修改状态为2,最后恢复到保存的状态,仍然是1。对象状态是通过Memento备忘录存储,而备忘录通过Caretaker管理进行创建和恢复。作为发起人只需要定义需要保存的范围和时机,符合迪米特法则。
注意事项:
- 备忘录创建出来就要在“最近”的代码中使用,要主动管理它的生命周期,建立就要使用,不使用就要立刻删除其引用,等待垃圾回收器对它的回收处理。
- 不要在频繁建立备份的场景中使用备忘录模式(比如一个for循环中),原因有二:一是控制不了备忘录建立的对象数量;二是大对象的建立是要消耗资源的,系统的性能需要考虑。
参考《设计模式之禅》秦小波著