Java设计模式之备忘录模式实现对象状态的保存和恢复

 更新时间:2023年04月23日 08:31:51   作者:.番茄炒蛋  
本文介绍Java设计模式之备忘录模式,该模式可以实现对象状态的保存和恢复。通过详细讲解备忘录模式的原理、实现方法和应用场景,帮助读者深入理解该设计模式,并提供示例代码和技巧,便于读者实际应用

介绍

备忘录模式(Memento Pattern)是一种行为型设计模式,它允许在不破坏封装性的前提下,捕获并保存一个对象的内部状态,并在之后可以恢复该对象到先前的状态.该模式的核心是备忘录(Memento)类,它储存了一个对象的内部状态.

在Java中,备忘录模式可以通过定义一个备忘录类来实现.备忘录类通常包含一个或多个私有字段来储存要保存的对象的内部状态.备忘录类还可以提供公共方法来获取和设置这些字段.原始对象可以使用备忘录类创建备忘录,并将其保存到历史记录中.在需要恢复对象的状态时,原始对象可以从历史记录中获取备忘录,并使用备忘录来恢复其状态.

在备忘录模式中,一般会涉及到以下三个角色:

  • Originator(发起人):它是要被保存状态的对象.它提供了创建备忘录和恢复备忘录的接口,允许其他对象获取其内部状态.
  • Memento(备忘录):它用于储存Originator内部状态得对象.备忘录可以根据Originator得需求来保存其内部状态,并且可以防止Originator以外得其他对象访问该状态.
  • Caretaker(管理者):它负责保存备忘录,并在需要时将其提供给Originator进行恢复,Caretaker可以储存多个备忘录,以及支持多次撤销操作.

在Java中实现备忘录模式时,一般会涉及到以上三个角色.其中Originator和Memento是必需的,Caretaker可以根据实际需要来选择是否实现.

实现

假设有一个游戏角色类Role,它有三个属性:attack(攻击力),defense(防御力)和hp(生命值).现在我们要实现一个备忘录模式,可以保存角色的状态,并在需要时恢复角色的状态.

备忘录类

@Data
public class Memento {
    /**
     * 攻击力
     */
    private int attack;
    /**
     * 防御力
     */
    private int defense;
    /**
     * 生命值
     */
    private int hp;
    public Memento(int attack, int defense, int hp) {
        this.attack = attack;
        this.defense = defense;
        this.hp = hp;
    }
}

发起人类

@Data
public class Role {
    /**
     * 攻击力
     */
    private int attack;
    /**
     * 防御力
     */
    private int defense;
    /**
     * 生命值
     */
    private int hp;
    public Role(int attack, int defense, int hp) {
        this.attack = attack;
        this.defense = defense;
        this.hp = hp;
    }
    /**
     * 将当前对象储存值Memento中
     * @return
     */
    public Memento save(){
        return new Memento(attack,defense,hp);
    }
    /**
     * 从memento中获取状态;并恢复到当前状态
     * @param memento
     */
    public void restore(Memento memento){
        attack = memento.getAttack();
        defense = memento.getDefense();
        hp = memento.getHp();
    }
}

管理者类

public class Caretaker {
    private List<Memento> mementos = new ArrayList<>();
    public void addMemento(Memento m){
        mementos.add(m);
    }
    public Memento getMemento(int index){
        return mementos.get(index);
    }
}

测试

public class Demo {
    public static void main(String[] args) {
        Role role = new Role(100,50,20);
        Caretaker caretaker = new Caretaker();
        Memento memento = role.save();
        caretaker.addMemento(memento);
        // 攻击力+10
        role.setAttack(role.getAttack()+10);
        System.out.println(JSON.toJSONString(role));
        // 恢复
        role.restore(caretaker.getMemento(0));
        System.out.println(JSON.toJSONString(role));
    }
}

这是一个完整的备忘录模式的例子.在这个例子中,我们创建一个备忘录类Memento,它保存了角色的攻击力,防御力和生命值.我们还创建了一个角色类Role,它可以保存和恢复角色的状态.最后.我们创建了一个Caretaker类,它用于保存Memento对象.通过这些类的结合使用,我们实现了备忘录模式.

总结

优点

  • 可以实现对象状态的保存和恢复,使得对象状态的变化更加灵活可控.
  • 模式实现简单,易于理解和使用.
  • 备忘录对象和原始对象分离,保证了系统的封装性.

缺点

  • 如果要保存的状态数据量比较大,备忘录对象可能会占用较大的内存空间.
  • 如果需要保存的状态比较频繁,备忘录对象的管理可能会变得比较复杂.

应用场景

  • 需要保存对象状态的历史记录,以便后续回退到之前的某个状态,例如文本编辑器中的撤销操作.
  • 需要对对象状态进行备份和恢复的场景,例如数据库中的事务管理.
  • 需要实现对象状态的快照,一边后续进行分析和统计,例如游戏中存档和回放功能.

总之Java备忘录模式适用于需要保存和恢复对象状态的场景,可以帮助开发者更好地管理对象状态的变化,提高系统的灵活性和可控性.

到此这篇关于Java设计模式之备忘录模式实现对象状态的保存和恢复的文章就介绍到这了,更多相关Java备忘录模式内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • java正则表达式学习笔记之命名捕获

    java正则表达式学习笔记之命名捕获

    这篇文章主要为大家详细介绍了java正则表达式中的命名捕获,感兴趣的小伙伴们可以参考一下
    2016-02-02
  • Java中浮点数精度问题的解决方法

    Java中浮点数精度问题的解决方法

    这篇文章给大家介绍了Java中浮点数精度问题的解决方法,本文给大家介绍的非常详细,有问题描述有原因分析,非常不错,具有参考借鉴价值,感兴趣的朋友一起看看吧
    2016-10-10
  • SparkStreaming整合Kafka过程详解

    SparkStreaming整合Kafka过程详解

    这篇文章主要介绍了SparkStreaming整合Kafka过程,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习吧
    2023-01-01
  • 基于spring data jpa @query返回map的踩坑记录

    基于spring data jpa @query返回map的踩坑记录

    这篇文章主要介绍了基于spring data jpa @query返回map的踩坑记录,具有很好的参考价值,如有错误或未考虑完全的地方,望不吝赐教
    2021-11-11
  • Java静态static与实例instance方法示例

    Java静态static与实例instance方法示例

    这篇文章主要为大家介绍了Java静态static与实例instance方法示例,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2023-08-08
  • restemplate请求乱码之content-encoding=“gzip“示例详解

    restemplate请求乱码之content-encoding=“gzip“示例详解

    RestTemplate从Spring3.0开始支持的一个HTTP请求工具,它提供了常见的REST请求方案的模板,及一些通用的请求执行方法 exchange 以及 execute,接下来通过本文给大家介绍restemplate请求乱码之content-encoding=“gzip“,需要的朋友可以参考下
    2024-03-03
  • springboot集成Swagger的方法(让你拥有属于自己的api管理器)

    springboot集成Swagger的方法(让你拥有属于自己的api管理器)

    在大型的项目中,如果你有非常多的接口需要统一管理,或者需要进行接口测试,那么我们通常会在繁杂地api中找到需要进行测试或者管理的接口,接下来通过本文给大家介绍springboot集成Swagger的方法让你拥有属于自己的api管理器,感兴趣的朋友一起看看吧
    2021-11-11
  • mybatis-plus团队新作mybatis-mate实现数据权限

    mybatis-plus团队新作mybatis-mate实现数据权限

    本文主要介绍了mybatis-plus 团队新作 mybatis-mate 轻松搞定数据权限,文中通过示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2021-09-09
  • Java工程中使用Mybatis (工程结合Mybatis,数据结合Swing使用))

    Java工程中使用Mybatis (工程结合Mybatis,数据结合Swing使用))

    这篇文章主要介绍了Java工程中使用Mybatis (工程结合Mybatis,数据可以结合Swing使用),需要的朋友可以参考下
    2017-04-04
  • Java校验是否为连续的区间问题

    Java校验是否为连续的区间问题

    这篇文章主要介绍了Java校验是否为连续的区间问题,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2023-12-12

最新评论