设计模式学习笔记--备忘录(Mamento)模式
写在模式学习之前
什么是设计模式:在我们进行程序设计时,逐渐形成了一些典型问题和问题的解决方式,这就是软件模式;每个模式描写叙述了一个在我们程序设计中常常发生的问题,以及该问题的解决方式;当我们碰到模式所描写叙述的问题,就能够直接用对应的解决方法去解决问题,这就是设计模式。
设计模式就是抽象出来的东西。它不是学出来的,是用出来的;也许你根本不知道不论什么模式。不考虑不论什么模式。却写着最棒的代码,即使以“模式专家”的角度来看,都是最佳的设计。不得不说是“最佳的模式实践”。这是由于你积累了非常多的实践经验,知道“在什么场合代码应该怎么写”,这本身就是设计模式。
有人说:“水平没到,学也白学,水平到了,无师自通”。
诚然,模式背熟,依旧可能写不出好代码。更别说设计出好框架。OOP理解及实践经验到达一定水平。同一时候也意味着总结了非常多好的设计经验。但"无师自通",却也未必尽然。或者能够说,恰恰是在水平和经验的基础上,到了该系统的学习一下“模式”的时候了。学习一下专家总结的结果。印证一下自己的不足,对于提高水平还是非常有帮助的。
本系列的设计模式学习笔记,实际是对于《Java与模式》这本书的学习记录。
备忘录模式的定义
备忘录模式(Memento Pattern),又叫快照模式(Snapshot Pattern)或Token模式,是对象的行为模式。
备忘录对象是一个用来存储还有一个对象内部状态的快照的对象。
备忘录模式的用意,是在不破坏封装(enscapsolution)的条件下。将还有一个对象的状态捕捉(capture)住,并外部(Externalize)化。存储起来,从来能够在将来合适的时候,把这个对象还原到存储起来的状态。
备忘录模式的结构
结构图
所涉及的角色
(1)备忘录(Memento)角色:将发起人(Originator)角色的内部状态存储起来,能够保护其状态不被发起人对象之外的不论什么对象读取。
(2)发起人(Originator)角色:创建一个含有当前内部状态的备忘录对象,使用备忘录对象存储其内部状态;
(3)负责人(Caretaker)角色:负责保存备忘录对象。不检查备忘录对象的内容。
从以上的职责能够看出。负载人(Caretaker)角色,不过把备忘录(Memento)角色存储起来。功能微小而单一,所以非常多时候,其功能也被集成到发起人(Originator)角色中。形成一种备忘录模式的变种,“自述历史”模式,这可能是备忘录模式的最流行的实现了。
记住这些模式的名字可真是麻烦,非常多时候,我们可能已经在须要快照的编程场景中使用过这样的模式了,但是。真的不知道是备忘录模式。是“自述历史”
代码实现
public class MementoTest {
public static void main(String[] args)
{
Originator o = new Originator();
Caretaker c = new Caretaker(); o.setState("On"); //更改发起人状态为On
System.out.println("Current State : " + o.getState());
c.setMemento(o.createMemento()); //存储快照
o.setState("Off"); //更改发起人状态为Off
System.out.println("Current State : " + o.getState());
o.restoreMemento(c.getMemento()); //从快照恢复状态
System.out.println("Current State : " + o.getState());
}
} class Memento
{
private String state;
public Memento(String state)
{
this.state = state;
}
public String getState() {
return state;
}
public void setState(String state) {
this.state = state;
}
}
class Originator
{
private String state;
/**
* 工厂方法,返回一个新的备忘录对象
*/
public Memento createMemento()
{
return new Memento(state);
}
/**
* 将发起人对象恢复到备忘录对象所记录的状态
*/
public void restoreMemento(Memento m)
{
this.state = m.getState();
}
public String getState() {
return state;
}
public void setState(String state) {
this.state = state;
}
}
class Caretaker{
private Memento memento;
public Memento getMemento() {
return memento;
}
public void setMemento(Memento memento) {
this.memento = memento;
}
}
备忘录模式的优缺点
长处:
(1)有时一些发起人对象的状态信息必须保存在发起人对象以外的地方。可是必须由发起人对象自己读取。
这时备忘录能够把发起人对象内部信息对其它对象屏蔽起来,从而能够恰当的保持封装的边界。
长处&缺点:
这个模式,简化了发起人(Originator)类;当然同一时候添加了备忘录(Memento)类和负责人(Caretaker)类。这算长处还是缺点呢?
仅仅能是我们依据详细的场景。依据实际情况进行选择。
备忘录模式的适用场景
(1)对无状态Http协议的支持技术。比方session、cookie;
(2)一些视窗软件的配置文件。关闭时保存状态,重新启动打开时自己主动到达关闭时的状态。
设计模式学习笔记--备忘录(Mamento)模式的更多相关文章
- 设计模式学习笔记-Adapter模式
Adapter模式,就是适配器模式,使两个原本没有关联的类结合一起使用. 平时我们会经常碰到这样的情况,有了两个现成的类,它们之间没有什么联系,但是我们现在既想用其中一个类的方法,同时也想用另外一个类 ...
- Java-马士兵设计模式学习笔记-装饰者模式
Java装饰者模式简介 一.假设有一个Worker接口,它有一个doSomething方法,Plumber和Carpenter都实现了Worker接口,代码及关系如下: 1.Worker.java p ...
- 研磨设计模式学习笔记2--外观模式Facade
需求:客户端需要按照需求,执行一个操作,操作包括一个系统中的3个模块(根据配置选择是否全部执行). 外观模式优点: 客户端无需知道系统内部实现,,只需要写好配置文件,控制那些模块执行,简单易用. 外观 ...
- 设计模式学习笔记 1.factory 模式
Factory 模式 用户不关心工厂的具体类型,只知道这是一个工厂就行. 通过工厂的实现推迟到子类里面去来确定工厂的具体类型. 工厂的具体类型来确定生产的具体产品. 同时用户不关心这是一个什么样子的产 ...
- 设计模式学习笔记——Composite 组合模式
用于描述无限层级的复杂对象,类似于描述资源管理器,抽象出每一个层级的共同特点(文件夹和文件,展开事件) 以前描述一个对象,是将整个对象的全部数据都描述清楚,而组合模式通过在对象中定义自己,描述自己的下 ...
- 设计模式学习笔记——Bridge 桥接模式
先说一下我以前对桥接模式的理解:当每个类中都使用到了同样的属性或方法时,应该将他们单独抽象出来,变成这些类的属性和方法(避免重复造轮子),当时的感觉是和三层模型中的model有点单相似,也就是让mod ...
- 设计模式学习笔记——Visitor 访问者模式
1.定义IVisitor接口,确定变化所涉及的方法 2.封装变化类.实现IVisitor接口 3.在实体类的变化方法中传入IVisitor接口,由接口确定使用哪一种变化来实现(封装变化) 4.在使用时 ...
- Java-马士兵设计模式学习笔记-责任链模式-FilterChain功能
一.目标 增加filterchain功能 二.代码 1.Filter.java public interface Filter { public String doFilter(String str) ...
- Java-马士兵设计模式学习笔记-责任链模式-处理数据
一.目标 数据提交前做各种处理 二.代码 1.MsgProcessor.java public class MsgProcessor { private List<Filter> filt ...
随机推荐
- 【SQL】约束与触发器1
一.外键 1.1特点 表A的外键,一定是其他某个表B的主键或有UNIQUE声明的属性. A的外键的值,一定是对应表B中相应的属性值.(空值除外) 1.2声明方法 方法1:属性名 类型 REFERENC ...
- hdu 1281(最小点覆盖数)
棋盘游戏 Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)Total Submis ...
- WN7下安装office2013编辑文档反应这么慢?
把office在高级选项里面“禁用硬件加速”给打勾就OK了. [office 2013密钥] 9MBNG-4VQ2Q-WQ2VF-X9MV2-MPXKV F2V7V-8WN76-77BPV-MKY36 ...
- Redis 源码走读(一)事件驱动机制与命令处理
eventloop 从 server.c 的 main 方法看起 int main(int argc, char **argv) { ....... aeSetBeforeSleepProc(serv ...
- Codeforces 189A. Cut Ribbon
题目链接:http://codeforces.com/problemset/problem/189/A 题意: 给你一个长度为 N 的布条, 再给你三个长度 a, b , c.你可以用剪刀去剪这些布条 ...
- 2018 ACM-ICPC 徐州网络赛
Problem A Problem B Problem C. 首先枚举那些他知道但是我不知道的数字.枚举这些的所有情况. 然后对每种情况再枚举我们都不知道的数字.求出每行每列的期望,求个最大值. 这样 ...
- 百度Map-JSAPI-覆盖物范围查询标记
1.单点标记并添加说明信息 2.可视化区域范围 3.矩形覆盖物经纬度范围 说明:该项目为javaweb项目,标记点信息为数据库中存储信息] 参考API链接 http://api.map.baidu.c ...
- 11.5NOIP2018提高组模拟题
书信(letter) Description 有 n 个小朋友, 编号为 1 到 n, 他们每人写了一封信, 放到了一个信箱里, 接下来每个人从中抽取一封书信. 显然, 这样一共有 n!种拿到书信的情 ...
- 18、Django实战第18天:课程机构收藏功能
这里点击"收藏"也是ajax异步操作,我在operation.model.py中创建了一个用户收藏表,其中fav_id字段,如果我们收藏的是课程,那就是课程id,如果收藏的是课程机 ...
- Python __call__内置函数的作用和用法
开学了进入了实验室,需要协助大师兄做事,主要是OpenStack中的代码解析,但是涉及很多python高级用法,一时间有点麻烦,在做项目的同时慢慢更新博客.这次先写一下__call__的用法,因为经常 ...