首页 > 其他分享 >设计模式之备忘录模式

设计模式之备忘录模式

时间:2022-10-06 15:24:57浏览次数:48  
标签:originator Console string 模式 备忘录 state ._ 设计模式 public

备忘录模式

概念

Memento is a behavioral design pattern that lets you save and restore the previous state of an object without revealing the details of its implementation.

备忘录模式是一种行为设计模式, 允许在不暴露对象实现细节的情况下保存和恢复对象之前的状态。

场景

在支持 Undo/Redo 的场景下面,如果需要撤销某一次行为的时候,在执行行为之前需要将数据保存下来。

备忘录模式指的是专门构造一个类似Snapshot的类,保存当时的一些数据信息,这些信息不能修改。

在撤销的时候,拿出来这些数据,以便恢复现场。

案例

首先实现记录现场的数据类,主要记录了当时的时间和文本

    public interface IMemento
    {
        string GetName();

        string GetState();

        DateTime GetDate();
    }

    class ConcreteMemento : IMemento
    {
        private string _state;

        private DateTime _date;

        public ConcreteMemento(string state)
        {
            this._state = state;
            this._date = DateTime.Now;
        }

        public string GetState()
        {
            return this._state;
        }

        public string GetName()
        {
            return $"{this._date} / ({this._state.Substring(0, 9)})...";
        }

        public DateTime GetDate()
        {
            return this._date;
        }
    }

 接着负责行为的类,会在恰当的时机,保存现场,生成这样一个对象

    class Originator
    {
        private string _state;

        public Originator(string state)
        {
            this._state = state;
            Console.WriteLine("Originator: My initial state is: " + state);
        }

        public void DoSomething()
        {
            Console.WriteLine("Originator: I'm doing something important.");
            this._state = this.GenerateRandomString(30);
            Console.WriteLine($"Originator: and my state has changed to: {_state}");
        }

        private string GenerateRandomString(int length = 10)
        {
            string allowedSymbols = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ";
            string result = string.Empty;

            while (length > 0)
            {
                result += allowedSymbols[new Random().Next(0, allowedSymbols.Length)];

                Thread.Sleep(12);

                length--;
            }

            return result;
        }

        public IMemento Save()
        {
            return new ConcreteMemento(this._state);
        }

        public void Restore(IMemento memento)
        {
            if (!(memento is ConcreteMemento))
            {
                throw new Exception("Unknown memento class " + memento.ToString());
            }

            this._state = memento.GetState();
            Console.Write($"Originator: My state has changed to: {_state}");
        }
    }

 然后实现Undo的manager类会把每一步行为都保存

class Caretaker
    {
        private List<IMemento> _mementos = new List<IMemento>();

        private Originator _originator = null;

        public Caretaker(Originator originator)
        {
            this._originator = originator;
        }

        public void Backup()
        {
            Console.WriteLine("\nCaretaker: Saving Originator's state...");
            this._mementos.Add(this._originator.Save());
        }

        public void Undo()
        {
            if (this._mementos.Count == 0)
            {
                return;
            }

            var memento = this._mementos.Last();
            this._mementos.Remove(memento);

            Console.WriteLine("Caretaker: Restoring state to: " + memento.GetName());

            try
            {
                this._originator.Restore(memento);
            }
            catch (Exception)
            {
                this.Undo();
            }
        }

        public void ShowHistory()
        {
            Console.WriteLine("Caretaker: Here's the list of mementos:");

            foreach (var memento in this._mementos)
            {
                Console.WriteLine(memento.GetName());
            }
        }
    }

 最终调用如下:

            Originator originator = new Originator("Super-duper-super-puper-super.");
            Caretaker caretaker = new Caretaker(originator);

            caretaker.Backup();
            originator.DoSomething();

            caretaker.Backup();
            originator.DoSomething();

            caretaker.Backup();
            originator.DoSomething();

            Console.WriteLine();
            caretaker.ShowHistory();

            Console.WriteLine("\nClient: Now, let's rollback!\n");
            caretaker.Undo();

            Console.WriteLine("\n\nClient: Once more!\n");
            caretaker.Undo();

            Console.WriteLine();

 

标签:originator,Console,string,模式,备忘录,state,._,设计模式,public
From: https://www.cnblogs.com/chenyingzuo/p/16757672.html

相关文章

  • 014——static应用知识:单例设计模式
    static应用知识:单例设计模式设计模式开发中经常遇到一些问题,一个问题通常有n种解法的,但其中肯定有一种解法是最优的,这个最优的解法被人总结出来了,称之为设计模式。......
  • 设计模式之中介者模式
    中介者模式概念Mediator isabehavioraldesignpatternthatletsyoureducechaoticdependenciesbetweenobjects.Thepatternrestrictsdirectcommunication......
  • 设计模式-原型模式
    自己实现自己的对象拷贝逻辑,这个原型模式就是所谓这个prototype模式,prototype这个模式的话呢,其实简单来说是这样子的,它的场景没有什么太具体的场景,就是说,如果我们现在手头......
  • 设计模式之迭代器模式
    迭代器模式概念Iterator isabehavioraldesignpatternthatletsyoutraverseelementsofacollectionwithoutexposingitsunderlyingrepresentation(list,......
  • JAVA设计模式-外观模式
    JAVA设计模式-外观模式介绍外观模式是一种结构型模式,主要是为了隐藏系统的复杂性,对外提供一个可以访问的接口,客户端只需要访问这个接口即可。例如:我们现在的智能家居中......
  • 设计模式-构造器模式
    封装复杂对象的构造逻辑,那么这讲的话呢,实际上是这个builder模式,这个构造器模式就是builder,ok,那么这个builder模式所要实现的是一个什么场景呢,就是,是这样的,比如说我们现在要......
  • Red Hat Enterprise Linux release 8.0 (Ootpa)-进入单用户模式重新设置root密码
    RedHatEnterpriseLinuxrelease8.0使用单用户模式有一个前提,即系统引导器(GRUB)能正常工作;否则,就要使用修复模式进行系统维护。需要注意的是,进入单用户模式后,如果没有开......
  • 设计模式之责任链模式
    责任链模式概念ChainofResponsibility isabehavioraldesignpatternthatletsyoupassrequestsalongachainofhandlers.Uponreceivingarequest,each......
  • 设计模式之命令模式
    命令模式概念Command isabehavioraldesignpatternthatturnsarequestintoastand-aloneobjectthatcontainsallinformationabouttherequest.Thistra......
  • 5-互评-OO之接口-DAO模式代码阅读及应用
    DAO模式是接口的一个典型应用。阅读附件中的参考代码,并回答以下问题:StudenDaoListImpl.java与StudentDaoArrayImpl.java有何不同?StudenDaoListImpl.java采用List存......