命令模式
# 命令模式
// 命令基类
class command
{
public:
command() {}
virtual ~command() {}
public:
virtual void execute() = 0;
virtual void undo() = 0;
virtual void redo() = 0;
virtual bool canExecute() = 0;
virtual bool canUndo() = 0;
virtual bool canRedo() = 0;
virtual string serialize() = 0;
virtual void deSerialize(const string data) = 0;
};
// 命令仓库
class cmdStorage
{
public:
cmdStorage() {}
~cmdStorage() {}
public:
stack<command*>* operator->() {
return &storage;
}
virtual string serialize() {
return "";
};
virtual void deSerialize(const string data) {};
private:
stack<command*> storage;
};
// 命令管理
class cmdManager
{
public:
cmdManager() {}
~cmdManager() {}
public:
bool exec(command* cmd) {
bool ret = cmd->canExecute();
if (ret) {
cmd->execute();
undoStorage->push(cmd);
}
return ret;
}
bool undo() {
bool ret = undoStorage->size() > 0 ? true : false;
if (ret) {
command* cmd = undoStorage->top();
undoStorage->pop();
ret = cmd->canUndo();
if (ret) {
cmd->undo();
redoStorage->push(cmd);
}
else {
cout << "cmd can't undo" << endl;
}
}
else {
cout << "have no cmd" << endl;
}
return ret;
}
bool redo(){
bool ret = redoStorage->size() > 0 ? true : false;
if (ret) {
command* cmd = redoStorage->top();
redoStorage->pop();
ret = cmd->canRedo();
if (ret) {
cmd->redo();
undoStorage->push(cmd);
}
else {
cout << "cmd can't redo" << endl;
}
}
else {
cout << "have no cmd" << endl;
}
return ret;
}
private:
cmdStorage undoStorage;
cmdStorage redoStorage;
};
// concrete command test
class commandOne: public command
{
public:
commandOne() {}
~commandOne() {}
public:
virtual void execute() {
cout << "commandOne execute()" << endl;
}
virtual void undo() {
cout << "commandOne undo()" << endl;
}
virtual void redo() {
cout << "commandOne redo()" << endl;
}
virtual bool canExecute() {
return true;
}
virtual bool canUndo() {
return true;
}
virtual bool canRedo() {
return true;
}
virtual string serialize() {
return "";
}
virtual void deSerialize(const string data) {
}
};
class commandTwo : public command
{
public:
commandTwo() {}
~commandTwo() {}
public:
virtual void execute() {
cout << "commandTwo execute()" << endl;
}
virtual void undo() {
cout << "commandTwo undo()" << endl;
}
virtual void redo() {
cout << "commandTwo redo()" << endl;
}
virtual bool canExecute() {
return true;
}
virtual bool canUndo() {
return true;
}
virtual bool canRedo() {
return true;
}
virtual string serialize() {
return "";
}
virtual void deSerialize(const string data) {
}
};
void test_command(){
cmdManager manager;
commandOne* cmd1 = new commandOne();
commandTwo* cmd2 = new commandTwo();
// 输出: 1 2 2 1
cout << "test exec" << endl;
manager.exec(cmd1);
manager.exec(cmd1);
manager.exec(cmd2);
manager.exec(cmd2);
cout << "test undo" << endl;
manager.undo();
manager.undo();
manager.undo();
manager.undo();
manager.undo();
cout << "test redo" << endl;
manager.redo();
manager.redo();
manager.redo();
manager.redo();
manager.redo();
system("pause");
return EXIT_SUCCESS;
}