备忘录模式

1 游戏角色状态恢复问题

游戏角色有攻击力和防御力,在战斗前有一组值,战斗后攻击力和防御力都会下降,现在需要在战斗结束后恢复到战斗前的攻击力和防御力。我们可以用备忘录模式来解决这个问题。

2 备忘录模式介绍

备忘录模式(Memento Pattern)在不破坏封装性的前提下捕获一个对象的内部状态,并在该对象之外保存这个状态,这样就可以在后续需要时回复该对象原先保存的状态。可以这样理解备忘录模式:现实生活中的备忘录是用来记录某些要去做的事情,或者是记录已经达成的共同意见,以防忘记。而在软件层面,备忘录模式有着相同的含义,备忘录对象主要用来记录一个对象的某种状态或某些数据,当要做回退时,可以从备忘录对象里获取原来的对象进行恢复。
角色分析:
1)Origintor:需要被保存状态的对象
2)Memento:备忘录对象,负责保存Origintor对象的内部状态
3)Caretaker:守护者对象,负责保存一个或多个备忘录对象
说明:如果希望保存多个Origintor对象的不同时刻的状态,Caretaker可以使用Map。


备忘录模式类图

3 代码实现

首先有一个备忘录类,用来记录游戏角色的攻击力和防御力:

public class Memento {
    private int attack;
    private int defense;

    public Memento(int attack, int defense) {
        this.attack = attack;
        this.defense = defense;
    }

    public int getAttack() {
        return attack;
    }

    public void setAttack(int attack) {
        this.attack = attack;
    }

    public int getDefense() {
        return defense;
    }

    public void setDefense(int defense) {
        this.defense = defense;
    }
}

守护类Caretaker用来存放各个时刻的备忘录对象实例,这里只有一个阶段即战斗前,所以直接用一个Memento类型的成员来存放:

// 守护者对象,保存游戏角色的状态
public class Caretaker {
    private Memento memento;

    public Memento getMemento() {
        return memento;
    }

    public void setMemento(Memento memento) {
        this.memento = memento;
    }
}

游戏角色类:

public class GameRole {
    private int attack;
    private int defense;

    // 根据当前状态创建备忘录对象
    public Memento createMemento() {
        return new Memento(attack, defense);
    }

    // 从备忘录对象恢复GameRole的状态
    public void recoverFromMemento(Memento memento) {
        this.attack = memento.getAttack();
        this.defense = memento.getDefense();
    }

    public void display() {
        System.out.println("游戏角色当前攻击力:" + attack + ",防御力:" + defense);
    }

    public int getAttack() {
        return attack;
    }

    public void setAttack(int attack) {
        this.attack = attack;
    }

    public int getDefense() {
        return defense;
    }

    public void setDefense(int defense) {
        this.defense = defense;
    }
}

客户端:

public class Client {
    public static void main(String[] args) {
        // 创建游戏角色
        GameRole gameRole = new GameRole();
        gameRole.setAttack(100);
        gameRole.setDefense(100);
        System.out.println("战斗前的状态:");
        gameRole.display();

        // 保存战斗前的状态到caretaker
        Caretaker caretaker = new Caretaker();
        caretaker.setMemento(gameRole.createMemento());

        // 战斗结束
        gameRole.setAttack(20);
        gameRole.setDefense(30);
        System.out.println("战斗结束后的状态:");
        gameRole.display();

        // 恢复都战斗前的状态
        gameRole.recoverFromMemento(caretaker.getMemento());
        System.out.println("恢复到战斗前的状态:");
        gameRole.display();
    }
}

输出结果:

战斗前的状态:
游戏角色当前攻击力:100,防御力:100
战斗结束后的状态:
游戏角色当前攻击力:20,防御力:30
恢复到战斗前的状态:
游戏角色当前攻击力:100,防御力:100
备忘录模式实现游戏角色状态恢复问题

4 备忘录模式的特点

1)备忘录模式给用户提供了一种可以恢复状态的机制,可以使用户能够比较方便地回到某个历史状态。
2)备忘录模式实现了信息的封装,使得用户不需要关心状态的保存细节。
3)如果类的成员变量过多,势必会占用比较大的资源,而且每一次保存都会消耗一定的内存。
4)适用的场景包括游戏存档、word文档中的撤销操作、浏览器的后退功能、数据库的事务管理等。
5)为节约内存,备忘录模式可以和原型模式配合使用。

©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。