备忘录模式

一、模式简介

定义:在不破坏封装性的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态,以便以后当需要时能将该对象恢复到原先保存的状态
场景:需要保存与恢复数据的场景,如玩游戏时中间结果的存档功能。需要提供一个可回滚操作的场景,如数据库事务的操作。

  • 角色结构:
  • 发起人(Originator)角色:记录当前时刻的内部状态信息,提供创建备忘录和恢复备忘录数据的功能,实现其他业务功能,它可以访问备忘录里的所有信息。
  • 备忘录(Memento)角色:负责存储发起人的内部状态,在需要的时候提供这些内部状态给发起人。
  • 管理者(Caretaker)角色:对备忘录进行管理,提供保存与获取备忘录的功能,但其不能对备忘录的内容进行访问与修改。

二、模式实现

public class Originator { -> 发起者
    private String state;

    public String getState() {
        return state;
    }

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

    public Memento create(){
        return new Memento(getState());
    }

    public void CtrlZ(Memento memento){
        this.setState(memento.getState());
    }

    public void CtrlY(Memento memento){
        this.setState(memento.getState());
    }
}

public class Memento implements Cloneable{ -> 备忘录
    private String state;
    private Memento next;

    public Memento(String state) {
        this.state = state;
    }

    public String getState() {
        return state;
    }

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

    public Memento getNext() {
        return next;
    }

    public void setNext(Memento next) {
        this.next = next;
    }
}

public class Caretaker { -> 管理者
    private Memento mementoZ;
    private Memento mementoY;

    public Memento getMementoZ() {
        if (mementoZ != null) {
            Memento get = mementoZ;
            mementoZ = mementoZ.getNext();
            get.setNext(null);
            return get;
        }
        return null;
    }

    public void setMementoZ(Memento mementoZ) {
        if (this.mementoZ != null){
            mementoZ.setNext(this.mementoZ);
        }
        this.mementoZ = mementoZ;
    }

    public Memento getMementoY() {
        if (mementoY != null) {
            Memento get = mementoY;
            mementoY = mementoY.getNext();
            get.setNext(null);
            return get;
        }
        return null;
    }

    public void setMementoY(Memento mementoY) {
        if (this.mementoY != null){
            mementoY.setNext(this.mementoY);
        }
        this.mementoY = mementoY;
    }

    public void displayY() {
        display(mementoY);
    }

    public void displayZ() {
        display(mementoZ);
    }

    private void display(Memento memento) {
        if (memento != null) {
            System.out.println(memento.getState());
            if (memento.getNext() != null) display(memento.getNext());
        }
    }
}

以编辑记事本为例子,编辑过程可以先后退到某一时间的进度,再重新前进到某一时间的进度,管理者包含了两个备忘录,分别是后退(组合键:Ctrl + Z)和前进(组合键:Ctrl + Y),发起人通过管理者获取到备忘录,轻松回到某一时间的进度。

Originator originator = new Originator();
Caretaker caretaker = new Caretaker();

originator.setState("s1");
caretaker.setMementoZ(originator.create());
originator.setState("s2");
caretaker.setMementoZ(originator.create());
originator.setState("s3");
System.out.println("当前状态:"+originator.getState());

caretaker.setMementoY(originator.create());
originator.CtrlZ(caretaker.getMementoZ());
System.out.println("当前状态:"+originator.getState());

caretaker.setMementoY(originator.create());
originator.CtrlZ(caretaker.getMementoZ());
System.out.println("当前状态:"+originator.getState());

caretaker.setMementoZ(originator.create());
originator.CtrlY(caretaker.getMementoY());
System.out.println("当前状态:"+originator.getState());

caretaker.setMementoZ(originator.create());
originator.CtrlY(caretaker.getMementoY());
System.out.println("当前状态:"+originator.getState());

你可能感兴趣的:(备忘录模式)