设计模式--备忘录模式C++实现
备忘录模式C++实现
1定义Memento pattern
在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态。这样以后就可以将该对象恢复到原先的状态
2类图
3实现
class Originator
{
private:
string state;
public:
string getState();
void setState(string &x);
Memento creatMemento()
{
return new Memento(state);
}
void restoreMemento(Memento men)
{
setState(men.getState());
}
};
class Memento
{
public:
Memento(string st)
:state(st)
{}
string getState()
{
return state;
}
void setState(string st)
{
state = st;
}
};
//备忘录管理员角色
class Caretaker
{
private:
Memento memento;
Memento getMemento()
{return memento;}
void setMemento(string st)
{memento = st;}
};
class Client
{
public:
void operator()()
{
Originator or= new Originator();
Caretaker ca = new Caretaker();
//管理员备忘记录设置为用户定义为备忘状态
ca.setMemento(or.createMemento());
//用户重新会退到管理员记录的某一状态
or.restoreMemento(ca.getMemento());
}
};
4应用
使用场景
需要提供保存和恢复数据的相关状态场景
提供一个可回滚rollback操作
需要监控的副本场景。
数据库连接的事务管理就是备忘录模式
注意事项:
备忘录的声明期:作用在最近的代码。不使用就立即删除。..备忘录不是华佗在世,起死回生
备忘录的性能:不能用在for中,不能用频繁建立。消耗资源太多,这会是设计重构的前兆
5扩展
clone方式的备忘录
实现
class Originator :public Cloneable
{
private:
string state;
public:
void setState(string st);
Originator creatorMemento()
{
return clone();
}
restoreMemento(Originator or)
{
setState(or.getState);
}
Originator clone()
{
//其实就是拷贝构造一个
}
};
class Caretaker
{
private:
Originator or;
Originator getOriginator()
{
return or;
}
void setOriginator(Originator originator)
{
or = originator;
}
}
既然可以合并备忘录角色,那么管理员也是可以合并的
∴
class Originator :public Cloneable
{
private:
Originator* _backup;
string _state;
public:
Originator(const Originator& or)
{}
void setState();
void creatMemento()
{
_bcakup = new Originator(*this);
}
void restoreMemento()
{
assert(_backup);
setStat(_backup->getState);
}
};
注:因为clone方式的备忘录可能会因为深浅拷贝问题而复杂,所以clone方式的备忘录适用简单的场景
②多状态备忘录
在Originator中封装多个状态,而Memento则保存一个HashMap 的state
③多备份的备忘录
注:管理员角色封装一的HashMap封装一个备忘录而非备忘状态
eg
class Caretaker
{
private:
HashMap<string,Memento> memMap;
public:
Memento getMemento(stirng index)
{}
void setMemento(string index,Memento me)
{
memMap.put(index,me);
}
};
void Test
{
Originator or = new Originator();
Caretaker ca = new Caretaker();
ca.setMemento("001",or.createMemento());
ca.setMemento("002",or.createMemento());
or.restoreMemento(ca.getMemento("001"));
}
注:该模式下应当注意备忘录上限,控制内存
提升:提供权限问题
class Originator
{
private:
string state;
public:
void setState(string st);
Imemento createMemento()
{
return new Memento(state);
}
void restoreMemento(Imemento me)
{
setState(me.getState());
}
private:
//内置类,实现
class Memento :public IMemento
{
private:
string state;
Memento(string st)
{
state = st;
}
string getState();
void setState(string st);
};
};
class Imemento
{
public:
virtual ~Imemento()=0;
};
class Caretaker
{
Imemento memento;
public:
Imemento getMemento()
{
return memento;
}
void setMemento(Imemento mem)
{
memento = mem;
}
};
注:这里的设计方案:双接口设计,一个是业务的正常接口,实现必要的业务逻辑,宽接口;另一个则是空接口,什么方法都没有,目的是提供给子系统外的模块访问,窄接口。窄接口中没有任何操纵数据的方法,所以是相对安全的。
设计模式--备忘录模式C++实现的更多相关文章
- [转] Android中的设计模式-备忘录模式
转自Android中的设计模式-备忘录模式 定义 备忘录设计模式的定义就是把对象的状态记录和管理委托给外界处理,用以维持自己的封闭性. 比较官方的定义 备忘录模式(Memento Pattern)又叫 ...
- Java设计模式—备忘录模式
个人感觉备忘录模式是一个比较难的设计模式,备忘录模式就是一个对象的备份模式,提供了一种程序数据的备份方法. 定义如下:在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态.这样以 ...
- JAVA 设计模式 备忘录模式
用途 备忘录模式 (Memento) 在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态. 这样以后就可将该对象恢复到原先保存的状态. 备忘录模式是一种行为型模式. 结构
- [工作中的设计模式]备忘录模式memento
一.模式解析 备忘录对象是一个用来存储另外一个对象内部状态的快照的对象.备忘录模式的用意是在不破坏封装的条件下,将一个对象的状态捕捉(Capture)住,并外部化,存储起来,从而可以在将来合适的时候把 ...
- 深入浅出设计模式——备忘录模式(Memento Pattern)
模式动机 为了使软件的使用更加人性化,对于误操作,我们需要提供一种类似“后悔药”的机制,让软件系统可以回到误操作前的状态,因此需要保存用户每一次操作时系统的状态,一旦出现误操作,可以把存储的历史状态取 ...
- IOS设计模式-备忘录模式
内容大纲 如何存储记录 备忘录模式的基本原理 使用备忘录模式 优化存储方案 恢复UIView的状态 1.如何存储记录 在存储记录时,第一步我们需要用一把钥匙去打开一把锁.第二步,当我们打开锁之后就会有 ...
- PHP设计模式——备忘录模式
声明:本系列博客參考资料<大话设计模式>,作者程杰. 备忘录模式又叫做快照模式或Token模式,在不破坏封闭的前提下.捕获一个对象的内部状态,并在该对象之外保存这个状态.这样以后就可将该对 ...
- java设计模式---备忘录模式
一.引子 俗话说:世上难买后悔药.所以凡事讲究个"三思而后行",但总常见有人做"痛心疾首"状:当初我要是--.如果真的有<大话西游>中能时光倒流的& ...
- C++设计模式——备忘录模式
备忘录模式 在GOF的<设计模式:可复用面向对象软件的基础>一书中对备忘录模式是这样说的:在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态.这样以后就可将该对象恢 ...
- C#设计模式-备忘录模式
访问者模式的实现是把作用于某种数据结构上的操作封装到访问者中,使得操作和数据结构隔离.而本文要介绍的备忘者模式与命令模式有点相似,不同的是,命令模式保存的是发起人的具体命令(命令对应的是行为),而备忘 ...
随机推荐
- php实现异步的程序调用
浏览器和服务器之间的通信是基于HTTP协议进行链接通讯的,它是一种请求和相应的协议.浏览器通过URL向服务器发送请求,服务器接收到请求并执行请求,然后服务器将执行完成的数据返回到客户端. 这就存在一个 ...
- 《FLASH PROGRAMMING 那些事》总结
注明来自 http://www.ssdfans.com/?p=5589 以MLC为例: 对FGF(Floating Gate Flash)技术的,MLC programming一般分两步走:先prog ...
- PHP 基础篇 - PHP 错误级别详解
一.前言 最近经常看到工作 2 年左右的童鞋写的代码也会出现以静态方法的形式调用非静态方法,这是个 Deprecated 级别的语法错误,代码里不应该出现的.对方很郁闷,说:为什么我的环境可以正常运行 ...
- ACM零散知识
定理与方法专区: 1.两点间的曼哈顿距离如果为偶数,那么两点间可以走偶数步到达 2.求小于等于n 的素数的个数.(即欧拉函数) 100=(2^2)*(5^2) num[100]=(2+1)*(2 ...
- Linux系统——账号管理
用户账号管理 分类: 超级用户 root uid=0 gid=0 权限最大 普通用户 uid=>500 ,一般权限的系统管理 程序用户 1=<uid,为了提升系统安全性,支持所对应服务对系 ...
- Maven的plugins、pluginManagement和dependencies、dependencyManagement
plugins和dependencies下边配的都是真实使用的. pluginManagement和dependencyManagement下边配的都只是做声明的,一般配置在顶级pom中. 参考链接: ...
- iOS 绘制一个表盘时钟,秒针效果可以“扫秒/游走”
最近自己 也尝试写了一个表盘时钟,初衷源于等车时候一个老奶奶问时间,我打开手机,时间数字对我来说相对敏感,但是老奶奶是看不清的,我想识别 还是看表盘 老远 看时针分针角度就可以识别当前时间. 于是我想 ...
- TOSCA自动化测试工具--How to modify windows
1.页面窗口(高亮的部分是我们需要的所有窗口) 2.窗口可以任意拖拽到任何地方 3.窗口可以并列显示 任务栏点击按钮可以继续拖动 放到自己想放的地方 4.收起preview,调整宽窄 5.保存当前wi ...
- java虚拟机-垃圾回收算法
在Java中,程序员不需要去关心内存动态分配和垃圾回收的问题,这一切都交给了JVM来处理.但是首先需要明确,什么样的对象才能当为垃圾: 1.引用计数法:如果某个引用(即指针)指向对象,那么说明该对象还 ...
- CentOS 64位系统 yum安装32位软件包的方法
//假如你要安装libjpeg的32位版本 1.查询具体的32位版本,然后安装 yum search libjpeg.i686 yum -y install libjpeg.i386 2.一劳永逸的方 ...