首页 > 其他分享 >一起学习设计模式:备忘录模式——软件的“后悔药”

一起学习设计模式:备忘录模式——软件的“后悔药”

时间:2022-10-09 23:31:09浏览次数:47  
标签:状态 life 原发 备忘录 后悔药 time 设计模式 Memento

一起学习设计模式:备忘录模式——软件的“后悔药”_历史状态

备忘录模式——软件的“后悔药”

备忘录是一种行为设计模式,允许在不暴露对象实现细节的情况下保存和恢复对象之前的状态, 并将其保存下来。

备忘录模式就像是软件中的“后悔药”,可以在软件中实现后悔机制的设计模式。

比如说很多游戏和软件中的撤销功能,这个功能可以让系统恢复到某个历史状态(最近的快照),在实现撤销时,首先必须保存软件系统的历史状态,当用户需要取消错误操作并且返回到某个历史状态时,可以取出事先保存的历史状态来覆盖当前状态:

一起学习设计模式:备忘录模式——软件的“后悔药”_历史状态_02

备忘录模式正是为了解决此类撤销问题而诞生,它为软件提供了“后悔药”,通过使用备忘录模式可以使系统恢复到某一特定的历史状态。

定义

备忘录模式(Memento Pattern):在不破坏封装的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态,这样可以在以后将对象恢复到原先保存的状态。其别名也叫 Token。

模式结构:

一起学习设计模式:备忘录模式——软件的“后悔药”_系统恢复_03

  • Originator(原生器):它是一个普通类,可以创建一个备忘录,并存储其当前内部状态,也可以使用备忘录来恢复其内部状态,一般需要保存内部状态的类设计为原发器。类可以生成自身状态的快照,也可以在需要时通过快照恢复自身状态。
  • Memento(备忘录):存储原发器的内部状态,根据原发器来决定保存哪些内部状态。备忘录的设计一般可以参考原发器的设计,根据实际需要确定备忘录类中的属性。是原发器状态快照的值对象 (value object)。通常做法是将备忘录设为不可变的,并通过构造函数一次性传递数据。
  • Caretaker(负责人):负责人又称为管理者,它负责保存备忘录,但是不能对备忘录的内容进行操作或检查。在负责人 类中可以存储一个或多个备忘录对象,它只负责存储对象,而不能修改对象,也无须知道对象的实现细节。仅知道“何时”和“为何”捕捉原发器的状态,以及何时恢复状态。

代码:

import java.util.List;
import java.util.ArrayList;

class Life
{
private String time;

public void set(String time)
{
System.out.println("Setting time to " + time);
this.time = time;
}

public Memento saveToMemento()
{
System.out.println("Saving time to Memento");
return new Memento(time);
}

public void restoreFromMemento(Memento memento)
{
time = memento.getSavedTime();
System.out.println("Time restored from Memento: " + time);
}

public static class Memento
{
private final String time;

public Memento(String timeToSave)
{
time = timeToSave;
}

public String getSavedTime()
{
return time;
}
}
}

class Design
{

public static void main(String[] args)
{

List<Life.Memento> savedTimes = new ArrayList<Life.Memento>();

Life life = new Life();

//time travel and record the eras
life.set("1000 B.C.");
savedTimes.add(life.saveToMemento());
life.set("1000 A.D.");
savedTimes.add(life.saveToMemento());
life.set("2000 A.D.");
savedTimes.add(life.saveToMemento());
life.set("4000 A.D.");

life.restoreFromMemento(savedTimes.get(0));

}
}

优缺点

优点:

  • 你可以在不破坏对象封装情况的前提下创建对象状态快照。
  • 你可以通过让负责人维护原发器状态历史记录来简化原发器代码。

缺点:

  • 如果客户端过于频繁地创建备忘录,程序将消耗大量内存。
  • 负责人必须完整跟踪原发器的生命周期,这样才能销毁弃用的备忘录。
  • 绝大部分动态编程语言(例如 PHP、 Python 和 JavaScript)不能确保备忘录中的状态不被修改。

标签:状态,life,原发,备忘录,后悔药,time,设计模式,Memento
From: https://blog.51cto.com/yuzhou1su/5742176

相关文章

  • 设计模式-行为型模式之模板方法
    定义抽象基类,规范接口内部方法执行顺序在进阶篇中,没专门提过抽象基类,在这里顺便就提一下抽象基类的核心特征:不能被直接实例化相反,抽象基类和元类一样,一般都被当......
  • Java设计模式 —— 组合模式
    9组合模式9.1组合模式概述CompositePattern:组合多个对象形成树形结构以表示具有部分-整体关系的层次结构。组合模式使得客户端可以统一处理单个对象和组合对象。......
  • 3 设计模式-建造者模式
    建造者模式在现实生活中如果我们需要制造一个比较复杂的东西,比如手机,台式电脑,或者汽车等。如果我们要制造一台电脑的话我们会先将电脑所需的各个部件买回来然后在组装起......
  • 设计模式 -- Facade(门面模式)
    门面模式(Facade)系统间耦合的复杂度对于客户系统和子系统之前存在很多的耦合的情况,如果不考虑设计的情况,那么会形成A方案的情况,系统的依赖严重,维护性大大降低。如果在......
  • 设计模式在美团外卖营销业务中的实践
     业务策略多变导致需求多变,是业界很多技术团队面临的最具挑战的问题之一。那么如何设计一套易于扩展和维护的营销系统呢?  今天的文章来自美团外卖营销技术团队,他们分享......
  • 初识设计模式 - 外观模式
    简介外观设计模式(FacadeDesignPattern)又被叫作门面模式,其描述是,通过为多个复杂的子系统提供统一的接口,使得子系统更容易被使用。在现实生活中,常常存在办事复杂的情况,如......
  • 设计模式-策略模式
    策略模式,替换掉屎一样的if-else语句。好,那我们来在这里看一下啊,就是整个,这个策略模式呢,它的英文叫做strategy,然后,就给出一个场景吧,还是,这个场景其实也很简单,就是说是,我们可......
  • 设计模式-组合模式
    对层级数据递归调用执行操作。先说一下这个组合模式是composite,然后说一个场景,这个模式然后按照一个什么场景来做呢,举个例子,有一颗部门树,然后父部门有这个子部门,然后又有子......
  • 08-Go设计模式-外观模式
    外观模式示例代码/*外观模式根据迪米特法则,如果两个类不必彼此直接通信,那么这两个类就不应当发生直接的相互作用。Facade模式也叫外观模式,是由GoF提出的23种设计模式......
  • 07-Go设计模式-适配模式
    适配模式示例代码/*适配器模式:将一个类的接口转换成客户希望的另外一个接口。使得原本由于接口不兼容而不能一起工作的那些类可以一起工作。适配器模式中的角色和......