一、概述

  又叫做快照模式(Snapshot Pattern)或Token模式

  保存对象的内部状态,并在需要的时候(undo/rollback)恢复对象以前的状态。

  意图:在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态。

  主要解决:所谓备忘录模式就是在不破坏封装的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态,这样可以在以后将对象恢复到原先保存的状态。

  备忘录模式和状态模式:备忘录模式是对象表示状态,状态模式是用类来表示状态。

1.1、适用场景

  1、需要保存/恢复数据的相关状态场景。 2、提供一个可回滚的操作。

  (1)一个类需要保存它的对象的状态(相当于Originator角色)
  (2)设计一个类,该类只是用来保存上述对象的状态(相当于Memento角色)
  (3)需要的时候,Caretaker角色要求Originator返回一个Memento并加以保存
  (4)undo或rollback操作时,通过Caretaker保存的Memento恢复Originator对象的状态

1.2、优缺点

  优点: 1、给用户提供了一种可以恢复状态的机制,可以使用户能够比较方便地回到某个历史的状态。 2、实现了信息的封装,使得用户不需要关心状态的保存细节。

  缺点:消耗资源。如果类的成员变量过多,势必会占用比较大的资源,而且每一次保存都会消耗一定的内存。

1.3、类图角色及其职责

  

  1、Originator(原生者):需要被保存状态以便恢复的那个对象,负责创建一个备忘录Memento,用以记录当前时刻自身的内部状态,并可使用备忘录恢复内部状态。Originator可以根据需要决定Memento存储自己的哪些内部状态。

  2、Memento(备忘录):该对象由Originator创建,主要负责存储Originator对象的内部状态,并可以防止Originator以外的其他对象访问备忘录。备忘录有两个接口:Caretaker只能看到备忘录的窄接口,他只能将备忘录传递给其他对象。Originator却可看到备忘录的宽接口,允许它访问返回到先前状

态所需要的所有数据。

  3、Caretaker(管理者):负责在适当的时间保存/恢复Originator对象的状态,负责备忘录Memento,不能对Memento的内容进行访问或者操作。

1.4、演进过程

首先,新建一个Person类,他就是Originator(原生者)

/*
* Originator(原生者)
*/
public class Person {
/*
* 姓名,年龄,性别就是结构图中的state,状态属性
*/
//姓名
private String name;
//年龄
private int age;
//性别
private String sex; public Person() {
super();
} public Person(String name, int age, String sex) {
super();
this.name = name;
this.age = age;
this.sex = sex;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} public int getAge() {
return age;
} public void setAge(int age) {
this.age = age;
} public String getSex() {
return sex;
} public void setSex(String sex) {
this.sex = sex;
} public void display() {
System.out.println("name:" + name + ",sex:" + sex + ",age:" + age);
} //创建一个备份
public Memento createMemento() {
return new Memento(name, age, sex);
} //恢复一个备份
public void setMemento(Memento memento) {
this.name = memento.getName();
this.age = memento.getAge();
this.sex = memento.getSex();
}
}

接着,创建一个Memento(备忘录),他和Originator的基本结构是一样的

/*
* Memento(备忘录)
*/
public class Memento {
//姓名
private String name;
//年龄
private int age;
//性别
private String sex; public Memento() {
super();
} public Memento(String name, int age, String sex) {
super();
this.name = name;
this.age = age;
this.sex = sex;
} public String getName() {
return name;
} public void setName(String name) {
this.name = name;
} public int getAge() {
return age;
} public void setAge(int age) {
this.age = age;
} public String getSex() {
return sex;
} public void setSex(String sex) {
this.sex = sex;
}
}

创建管理者Caretaker(管理者)角色

/*
* Caretaker(管理者)
*/
public class Caretaker {
//持有一个对Memento的引用
private Memento memento; public Memento getMemento() {
return memento;
} public void setMemento(Memento memento) {
this.memento = memento;
}
}

测试

    @Test
public void test() {
Person person = new Person("小明",18,"男");
//打印
person.display(); //创建一个管理者
Caretaker caretaker = new Caretaker(); //创建一个备份
// Memento memento = person.createMemento();
caretaker.setMemento(person.createMemento()); person.setName("小红");
person.setAge(17);
person.setSex("女");
//打印
person.display(); //备份还原
person.setMemento(caretaker.getMemento());
//打印
person.display();
}

输出

name:小明,sex:男,age:18
name:小红,sex:女,age:17
name:小明,sex:男,age:18

二、扩展

2.1、spring

org.springframework.binding.message.StateManageableMessageContext

数据库的事务管理。

004-行为型-07-备忘录模式(Memento)的更多相关文章

  1. c++ 行为型_备忘录模式(Memento)

    行为型_备忘录模式(Memento) 作用场景: 当意图在对象外面保存对象的内部状态,但是又不想破坏对象的封装性,就可以考虑备忘录模式. 解释: 其参与者包括 1.Memnto(备忘录,如下列Coun ...

  2. 【设计模式】行为型07备忘录模式(Memento Pattern)

    参考地址:http://www.runoob.com/design-pattern/memento-pattern.html 对原文总结调整,以及修改代码以更清晰的展示: 备忘录模式(快照模式):   ...

  3. 备忘录模式 Memento 快照模式 标记Token模式 行为型 设计模式(二十二)

    备忘录模式 Memento   沿着脚印,走过你来时的路,回到原点.     苦海翻起爱恨   在世间难逃避命运   相亲竟不可接近   或我应该相信是缘份   一首<一生所爱>触动了多少 ...

  4. 乐在其中设计模式(C#) - 备忘录模式(Memento Pattern)

    原文:乐在其中设计模式(C#) - 备忘录模式(Memento Pattern) [索引页][源码下载] 乐在其中设计模式(C#) - 备忘录模式(Memento Pattern) 作者:webabc ...

  5. 备忘录模式-Memento Pattern(Java实现)

    备忘录模式-Memento Pattern Memento备忘录设计模式是一个保存另外一个对象内部状态拷贝的对象,这样以后就可以将该对象恢复到以前保存的状态. 本文中的场景: 有一款游戏可以随时存档, ...

  6. 21备忘录模式Memento

    一.什么是备忘录模式 Memento模式也叫备忘录模式,是行为模式之 一,它的作用是保存对象的内部状态,并在需要 的时候(undo/rollback)恢复对象以前的状态. 二.备忘录模式的应用场景 如 ...

  7. Java 设计模式系列(十八)备忘录模式(Memento)

    Java 设计模式系列(十八)备忘录模式(Memento) 备忘录模式又叫做快照模式(Snapshot Pattern)或Token模式,是对象的行为模式.备忘录对象是一个用来存储另外一个对象内部状态 ...

  8. 二十四种设计模式:备忘录模式(Memento Pattern)

    备忘录模式(Memento Pattern) 介绍在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态.这样以后就可将该对象恢复到保存的状态. 示例有一个Message实体类,某 ...

  9. 设计模式之备忘录模式(Memento)

    备忘录模式(Memento) 在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态.这样以后就可将该对象恢复到原先保存的状态. Originator(发起人):负责创建一个备忘录 ...

  10. 行为型设计模式之备忘录模式(Memento)

    结构 意图 在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态.这样以后就可将该对象恢复到原先保存的状态. 适用性 必须保存一个对象在某一个时刻的(部分)状态, 这样以后需要时 ...

随机推荐

  1. 【Beta】 Scrum meeting 3

    第三天 日期:2019/6/26 前言 组内进行第三次讨论,所有组员都到场,项目已经全部完成. 一.今天任务完成情况.成员贡献时间 组员 任务 贡献时间 徐浩杰 完成项目的全部测试,项目运行稳定 2h ...

  2. 《发际线总是和我作对》第九次团队作业:【Beta】Scrum meeting1

    项目 内容 这个作业属于哪个课程 软件工程 这个作业的要求在哪里 实验十三 团队作业9:Beta冲刺与团队项目冲刺 团队名称 发际线总和我作队 作业学习目标 (1)掌握软件黑盒测试技术:(2)掌握软件 ...

  3. 「SDOI2016」征途

    征途 Pine开始了从S地到T地的征途. 从S地到T地的路可以划分成\(n\)段,相邻两段路的分界点设有休息站. Pine计划用\(m\)天到达T地.除第\(m\)天外,每一天晚上Pine都必须在休息 ...

  4. Ubuntu安装Apache 2.4.7常见问题解答

    环境:Apache 2.4.7 on Ubuntu 14.04 启动apache服务报错:Unknown Authz provider: ip 进入mod模块目录 cd /etc/apache2/mo ...

  5. Java - 基础到进阶

    # day01 一:基本操作 package _01.java基本操作; /** * 文档注释 */ public class _01Alls { public static void main(St ...

  6. 09 webpack的介绍

    webpack干嘛的?:  模块打包机,分析目录结构,找到js模块(包括浏览器不能直接识别的代码 typscript sass...),打包成合适的格式供浏览器访问 webpack是一款模块加载器兼打 ...

  7. JS数组去重整理合集

    1.利用splice var arr = [1,2,3,4,5,6,7,8,9,9,8,7,6,5,4,3,2,1]; function repeat(arr){ for(var i = 0;i< ...

  8. [TJOI2019]甲苯先生和大中锋的字符串

    有个叫asuldb的神仙来嘲讽我 说这题SAM水题,而且SA过不了 然后我就用SA过了 显然是一个Height数组上长为k的滑块,判一下两边,差分一下就可以了 #include"cstdio ...

  9. 网络请求之get post

    ——http get和post的区别? 1.get用于获取数据,post用于提交数据 2.get提交参数追加在url后面,post参数可以通过http body提交 3.get的url会有长度上的限制 ...

  10. vundle 管理插件

    前言:如果不使用vundle的话,进行插件的安装,配置和管理相对会麻烦,曾经没使用vundle的时候我经常遇到无法安装一些vim插件.但使用vundle后你只要在文件中添加一行你的插件名再安装就OK了 ...