备忘录模式——编程中的后悔药

来源:互联网 发布:量多空博弈指标源码 编辑:程序博客网 时间:2024/05/04 07:06

(《设计模式解析与实战——何红辉,关爱民》读书笔记)

一、定义
在不破坏封闭的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态,这样就可将该对象恢复到原先保存的状态。
比如,游戏的存档功能;Android中的onSaveInstanceState和onRestoreInstanceState;重做、撤销功能。

二、使用场景
(1)需要保存一个对象在某一时刻的状态或部分状态;
(2)如果用一个接口来让其他对象得到这些状态,将会暴露对象的实现细节并破坏对象的封装性,一个对象不希望外界直接访问其内部状态,通过中间对象可以间接访问其内部状态。

三、简单示例

/** * 备忘录类:这是一个无状态、无操作的实体类,只负责存储数据,防止外部直接访问内部状态 */public class Memorandum {    // 关卡    public int checkPoint;    // 生命值    public int lifeValue;    // 武器    public String weapon;    @Override    public String toString() {        return "Memorandum [checkPoint=" + checkPoint + ", lifeValue=" + lifeValue + ", weapon=" + weapon + "]";    }}
/** * 游戏 */public class Game {    private int mCheckpoint = 1; // 关卡    private int mLifeValue = 100; // 生命值    private String mWeapon = "沙漠之鹰"; // 武器    /**     * 玩游戏:对关卡和任务的生命值进行修改     */    public void play() {        System.out.println("打游戏:" + String.format("第%d关", mCheckpoint) + " 奋战杀敌中");        mLifeValue -= 10;        System.out.println("进度升级啦");        mCheckpoint++;        System.out.println("到达:" + String.format("第%d关", mCheckpoint));    }    /**     * 退出游戏     */    public void quit() {        System.out.println("-------------");        System.out.println("退出前的游戏属性:" + this.toString());        System.out.println("退出游戏");        System.out.println("-------------");    }    /**     * 创建备忘录:将自身的状态保存到备忘录对象中     */    public Memorandum createMemo() {        Memorandum memorandum = new Memorandum();        memorandum.checkPoint = mCheckpoint;        memorandum.lifeValue = mLifeValue;        memorandum.weapon = mWeapon;        return memorandum;    }    /**     * 恢复游戏:外部将状态从备忘录对象中恢复     */    public void restore(Memorandum memorandum) {        this.mCheckpoint = memorandum.checkPoint;        this.mLifeValue = memorandum.lifeValue;        this.mWeapon = memorandum.weapon;        System.out.println("恢复后的游戏属性:" + this.toString());    }    public int getmCheckpoint() {        return mCheckpoint;    }    public void setmCheckpoint(int mCheckpoint) {        this.mCheckpoint = mCheckpoint;    }    public int getmLifeValue() {        return mLifeValue;    }    public void setmLifeValue(int mLifeValue) {        this.mLifeValue = mLifeValue;    }    public String getmWeapon() {        return mWeapon;    }    public void setmWeapon(String mWeapon) {        this.mWeapon = mWeapon;    }    @Override    public String toString() {        return "Game [mCheckpoint=" + mCheckpoint + ", mLifeValue=" + mLifeValue + ", mWeapon=" + mWeapon + "]";    }}
/** * 负责管理备忘录对象 */public class Caretaker {    private Memorandum mMemorandum;    /**     * 存档     */    public void archive(Memorandum memorandum) {        this.mMemorandum = memorandum;    }    /**     * 获取存档     *      * @return mMemorandum:备忘录对象     */    public Memorandum getMemorandum() {        return mMemorandum;    }}
/** * 客户端 */public class Client {    public static void main(String[] args) {        // 构建游戏对象        Game game = new Game();        // 1、打游戏        game.play();        Caretaker caretaker = new Caretaker();        // 2、游戏存档        caretaker.archive(game.createMemo());        // 3、退出游戏        game.quit();        // 4、恢复游戏        Game restoreGame = new Game();        restoreGame.restore(caretaker.getMemorandum());    }}

运行结果:
这里写图片描述

四、总结
备忘录模式是在不破坏封装的条件下,通过备忘录对象存储另外一个对象内部状态的快照,在将来合适的时候把这个对象还原到存储起来的状态。
优点:
(1)给用户提供了一种可以恢复状态的机制,可以使用户能够比较方便的回到某个历史状态;
(2)实现了信息的封装,使得用户不需要关心状态的保存细节。
缺点:
消耗资源,如果类的成员变量过多,势必会占用比较大的资源,而且每一次保存都会消耗一定的内存。

0 0
原创粉丝点击