11.22

#include <iostream>

#include <stack>
#include <string>
using namespace std;
 
class Command
{
public:
    Command(){}
    virtual ~Command(){}
 
    virtual void Execute() = 0;
};
 
 
class InputCommand : public Command
{
    public:
 
        InputCommand( const std::string &input )
        {
            mInput = input;
        }
        ~InputCommand()
        {}
 
        void Execute()
        {
            printf( "当前字符串: %s\n", mInput.c_str() );
        }
 
private:
 
    std::string mInput;
};
 
class Commander
{
public:
    Commander( Command *pCmd )
    {
        //最初的命令数据
        mUndo.push( pCmd );
    }
    ~Commander()
    {
        whilefalse == mUndo.empty() )
        {
            delete mUndo.top();
            mUndo.pop();
        }
        whilefalse == mRedo.empty() )
        {
            delete mRedo.top();
            mRedo.pop();
        }
    }
 
    void ExecuteCommand( Command *pCmd )
    {
        pCmd->Execute();
        mUndo.push( pCmd );
    }
 
    void Undo()
    {
        if( mUndo.size() < 2 )
        {
            //无法后退撤销没有数据
            printf( "撤销失败.\n" );
            return;
        }
 
        printf( "撤销:\n" );
 
        //当前命令
        auto pCmd = mUndo.top();
 
        //保存当前命令
        mRedo.push( pCmd );
 
        //弹出
        mUndo.pop();
 
        //还原到上个命令
        pCmd = mUndo.top();
 
        pCmd->Execute();
    }
 
    void Redo()
    {
        if( mRedo.empty() )
        {
            //无法前进重做没有数据
            printf( "重写失败.\n" );
            return;
        }
 
        printf( "重写:\n" );
 
        auto pCmd = mRedo.top();
 
        pCmd->Execute();
 
        mRedo.pop();
 
        mUndo.push( pCmd );
    }
 
private:
    std::stack< Command* > mUndo;
    std::stack< Command* > mRedo;
};
 
int main()
{
    //默认没有输入字符串可以是空,这里为了演示赋值一个特殊的字符串
    Commander *p = new Commander( new InputCommand( "[empty]" ) );
 
    //输入1234
    p->ExecuteCommand( new InputCommand( "123" ) );
    //输入567
    p->ExecuteCommand( new InputCommand( "567" ) );
    //输入xxx
    p->ExecuteCommand( new InputCommand( "xxx" ) );
 
    //执行一次undo 撤销到 567
    p->Undo();
    //执行一次undo 撤销到 1234
    p->Undo();
 
    //undo后中间输入新字符串 insert 覆盖 1234
    p->ExecuteCommand( new InputCommand( "insert" ) );
 
    //执行一次undo 撤销到 1234
    p->Undo();
 
    //执行一次undo 撤销到最初情况 [empty]
    p->Undo();
 
    //执行失败已经undo 到最原始情况
    p->Undo();
 
    //执行一次redo 重做到 1234
    p->Redo();
    //执行一次redo 重做到 insert
    p->Redo();
    //执行一次redo 重做到 567
    p->Redo();
 
    //redo后中间输入新字符串 insert again 覆盖 567
    p->ExecuteCommand( new InputCommand( "insert again" ) );
 
    //执行一次undo 撤销到567
    p->Undo();
 
    //执行一次redo 重做到 insert again
    p->Redo();
 
    //执行一次redo 重做到 xxx
    p->Redo();
 
    //执行失败已经redo 到最新情况
    p->Redo();
    delete p;
    return 0;
}
posted @ 2021-11-22 19:21  韩佳龙  阅读(52)  评论(0编辑  收藏  举报