25 行为型模式-备忘录模式

1 备忘录模式介绍在这里插入图片描述

备忘录模式(memento pattern)定义: 在不破坏封装的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态,这样可以在以后将对象恢复到原先保存的状态.

2 备忘录模式原理

在这里插入图片描述
在这里插入图片描述

3 备忘录模式实现

在这里插入图片描述

/**
 * 发起人角色
 **/
public class Originator {

    private String state = "原始对象";

    private String id;

    private String name;

    private String phone;

    public Originator() {
    }

    //创建备忘录对象
    public Memento createMemento(){
        return new Memento(id,name,phone);
    }

    //恢复对象
    public void restoreMemento(Memento m){

        this.state = m.getState();
        this.id = m.getId();
        this.name = m.getName();
        this.phone = m.getPhone();
    }

    @Override
    public String toString() {
        return "Originator{" +
                "state='" + state + '\'' +
                ", id='" + id + '\'' +
                ", name='" + name + '\'' +
                ", phone='" + phone + '\'' +
                '}';
    }

    public String getState() {
        return state;
    }

    public void setState(String state) {
        this.state = state;
    }

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getPhone() {
        return phone;
    }

    public void setPhone(String phone) {
        this.phone = phone;
    }
}
/**
 * 备忘录角色
 * 访问权限为: 默认,在同包下可见(尽量保证只有发起者类可以访问备忘录类)
 **/
class Memento {

    private String state = "从备份对象恢复原始对象";

    private String id;

    private String name;

    private String phone;

    public Memento() {
    }

    public Memento(String id, String name, String phone) {
        this.id = id;
        this.name = name;
        this.phone = phone;
    }

    public String getState() {
        return state;
    }

    public void setState(String state) {
        this.state = state;
    }

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getPhone() {
        return phone;
    }

    public void setPhone(String phone) {
        this.phone = phone;
    }

    @Override
    public String toString() {
        return "Memento{" +
                "state='" + state + '\'' +
                ", id='" + id + '\'' +
                ", name='" + name + '\'' +
                ", phone='" + phone + '\'' +
                '}';
    }
}
/**
 * 负责人类-获取和保存备忘录对象
 **/
public class Caretaker {

    private Memento memento;

    public Memento getMemento() {
        return memento;
    }

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

    public static void main(String[] args) {

        //创建发起人对象
        Originator o1 = new Originator();
        o1.setId("1");
        o1.setName("spike");
        o1.setPhone("13522777722");
        System.out.println("========"+o1);

        //创建负责人对象
        Caretaker caretaker = new Caretaker();
        caretaker.setMemento(o1.createMemento());

        //修改
        o1.setName("update");
        System.out.println("========" + o1);

        //从负责人对象中获取备忘录对象,实现恢复操作
        o1.restoreMemento(caretaker.getMemento());
        System.out.println("========" + o1);
    }
}
4 备忘录模式应用实例

在这里插入图片描述

/**
 * 备份玩家的状态
 **/
class Memento {

    private int money;  //玩家获取的金币

    ArrayList fruits;  //玩家获取的水果

    public Memento(int money) {
        this.money = money;
        this.fruits = new ArrayList();
    }

    //获取当前玩家的金币
    public int getMoney(){
        return money;
    }

    //获取当前玩家的水果
    List getFruits(){
        return (List) fruits.clone();
    }

    //添加水果
    void addFruit(String fruit){
        fruits.add(fruit);
    }

}

Player玩家类,只要玩家的金币还够,就会一直进行游戏,在该类中会设置一个createMemento方法,其作用是保存当前玩家状态.还会包含一个restore撤销方法,相当于复活操作.

/**
 * 玩家类
 **/
public class Player {

    private int money;  //金币

    private List<String> fruits = new ArrayList<>();  //玩家获得的水果

    private static String[] fruitsName ={   //表示水果种类的数组
            "苹果","葡萄","香蕉","橘子"
    };

    Random random = new Random();

    public Player(int money) {
        this.money = money;
    }

    //获取当前所有金币
    public int getMoney(){
        return money;
    }

    //获取一个水果
    public String getFruit(){
        String prefix = "";
        if(random.nextBoolean()){
            prefix = "好吃的";
        }

        //从数组中拿一个水果
        String f = fruitsName[random.nextInt(fruitsName.length)];
        return prefix + f;
    }

    //掷骰子方法
    public void yacht(){

        int dice = random.nextInt(6) + 1; //掷骰子

        if(dice == 1){
            money += 100;
            System.out.println("所持有的金币增加了...");
        }else if(dice == 2){
            money /= 2;
            System.out.println("所持有的金币减少一半");
        }else if(dice == 6){ //获取水果
            String fruit = getFruit();
            System.out.println("获取了水果: " + fruit);
            fruits.add(fruit);
        }else{
            //其他结果
            System.out.println("无效数字,继续投掷!");
        }
    }

    //拍摄快照
    public Memento createMemento(){
        Memento memento = new Memento(money);
        for (String fruit : fruits) {

            //判断: 只保存 '好吃的'水果
            if(fruit.startsWith("好吃的")){
                memento.addFruit(fruit);
            }
        }

        return memento;
    }


    //撤销方法
    public void restoreMemento(Memento memento){
        this.money = memento.getMoney();
        this.fruits = memento.getFruits();
    }


    @Override
    public String toString() {
        return "Player{" +
                "money=" + money +
                ", fruits=" + fruits +
                '}';
    }
}

测试: 由于引入了备忘录模式,可以保存某个时间点的玩家状态,这样就可以对玩家进行复活操作.

public class MainApp {

    public static void main(String[] args) throws InterruptedException {

        //创建玩家类,设置初始金币
        Player player = new Player(100);

        //创建备忘录对象
        Memento memento = player.createMemento();

        for (int i = 0; i < 100; i++) {

            //显示扔骰子的次数
            System.out.println("第" + i+"次投掷!");

            //显示当前玩家状态
            System.out.println("当前状态: " + player);

            //开启游戏
            player.yacht();
            System.out.println("玩家所持有的金币: " + player.getMoney() + " 元");

            //复活操作
            if(player.getMoney() > memento.getMoney()){
                System.out.println("赚到金币,保存当前状态,继续游戏!");
                memento = player.createMemento();  //更新快照
            }else if(player.getMoney() < memento.getMoney() / 2){
                System.out.println("所持金币不多,将游戏恢复到初始状态!");
                player.restoreMemento(memento);
            }

            Thread.sleep(1000);
        }
    }
}
5 备忘录模式总结

在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值