【设计模式】加薪非要老总批 --- 职责链模式

来源:互联网 发布:电脑主题软件排行 编辑:程序博客网 时间:2024/05/16 09:09

一,概述

        定义:使多个对象都有机会处理请求,从而避免请求的发送者和接收者之间的耦合关系。将这个对象连成一条链,并沿着这条链传递该请求,直到有一个对象处理它为之。

        优点:客户提出请求时,请求时沿链传递直至有一个ConcreteHandler对象负责处理它

 

 

二,职责链基本代码

#include <iostream>using namespace std; class Handler{        protected: static  Handler *successor;        public: void SetSuccessor(Handler *successor)        {            this->successor = successor;        }        virtual void HandleRequest(int request)        {        } }; Handler* Handler::successor=NULL; //必须是static 变量才能在全局初始化     class ConcreteHandler1 :public Handler    {        public:   void HandleRequest(int request)        {            if (request >= 0 && request < 10)            {                cout<<"ConcreteHandler1"<<"处理请求"<<request<<endl;            }            else if (successor != NULL)            {                successor->HandleRequest(request);            }        }    };     class ConcreteHandler2 :public Handler    {        public:        void HandleRequest(int request)           {            if (request >= 10 && request < 20)            {                cout<<"ConcreteHandler2"<<"处理请求"<<request<<endl;            }            else if (successor != NULL)            {                successor->HandleRequest(request);            }        }    };     class ConcreteHandler3 :public Handler    {        public: void HandleRequest(int request)        {            if (request >= 20 && request < 30)            {                cout<<"ConcreteHandler3"<<"处理请求"<<request<<endl;            }            else if (successor != NULL)            {                successor->HandleRequest(request);            }        }    }; int main(){            Handler *h1 = new ConcreteHandler1();            Handler *h2 = new ConcreteHandler2();            Handler *h3 = new ConcreteHandler3();            h1->SetSuccessor(h2);//设置下一个             h2->SetSuccessor(h3);//设置下一个             int request[] = { 2, 5, 14, 22, 18, 3, 27, 20 };            for(int i=0;i<8;++i)            {                h1->HandleRequest(request[i]);            }                        return 0; }


三,示例

        小菜要求加薪,而加薪的批准需要总经理来批准。经理交给总监,总监交给总经理。

         缺点:Manager 类 太长,分支太多。如果要增加项目经理、部门经理等职位的话,需要更改原类,比较麻烦。

#include <iostream>using namespace std; //enum  ManagerLevel{ "经理","总监","总经理"} ManagerLevel;  enum  ManagerLevel{ manager,chief_inspector,president} ;        //申请    class Request    {        //申请类别        private: string requestType;        public: string getRequestType()        {            return requestType;         }         void setRequestType(string value)  {     requestType = value;          }        //申请内容        private: string requestContent;        public: string getRequestContent()        {             return requestContent;         }          void  setRequestContent(string value)   {      requestContent = value;    }                //数量        private: int number;        public: int getNumber() { return number;  }  void setNumber(int value)  {  this->number = value;  }    };      //管理者    class Manager    {                protected:   string name;        public: Manager(string name)        {            this->name = name;        }        //得到结果       void GetResult(ManagerLevel managerLevel, Request request)        {            if (managerLevel == manager)            {                if (request.getRequestType() == "请假" && request.getNumber() <= 2)                {                    //Console.WriteLine("{0}:{1} 数量{2} 被批准", name, request.RequestContent, request.Number);                    cout<<name<< request.getRequestContent()<<"数量"<< request.getNumber()<<"被批准"<<endl;                 }                else                {                cout<<name<< request.getRequestContent()<<"数量"<< request.getNumber()<<"我无权处理"<<endl;                     //Console.WriteLine("{0}:{1} 数量{2} 我无权处理", name, request.RequestContent, request.Number);                }            }            else if (managerLevel ==chief_inspector)            {                if (request.getRequestType() == "请假" && request.getNumber() <= 5)                {                cout<<name<< request.getRequestContent()<<"数量"<< request.getNumber()<<"被批准"<<endl;                     //Console.WriteLine("{0}:{1} 数量{2} 被批准", name, request.RequestContent, request.Number);                }                else                {                cout<<name<< request.getRequestContent()<<"数量"<< request.getNumber()<<"我无权处理"<<endl;                     //Console.WriteLine("{0}:{1} 数量{2} 我无权处理", name, request.RequestContent, request.Number);                }            }            else if (managerLevel == president)            {                if (request.getRequestType() == "请假")                {                cout<<name<< request.getRequestContent()<<"数量"<< request.getNumber()<<"被批准"<<endl;                     //Console.WriteLine("{0}:{1} 数量{2} 被批准", name, request.RequestContent, request.Number);                }                else if (request.getRequestType() == "加薪" && request.getNumber() <= 500)                {                cout<<name<< request.getRequestContent()<<"数量"<< request.getNumber()<<"被批准"<<endl;                    // Console.WriteLine("{0}:{1} 数量{2} 被批准", name, request.RequestContent, request.Number);                }                else if (request.getRequestType() == "加薪" && request.getNumber() > 500)                {                cout<<name<< request.getRequestContent()<<"数量"<< request.getNumber()<<"被批准"<<endl;                    // Console.WriteLine("{0}:{1} 数量{2} 再说吧", name, request.RequestContent, request.Number);                }            }        }    };            int main()        {            Manager *jinli = new Manager("金利");            Manager *zongjian = new Manager("宗剑");            Manager *zhongjingli = new Manager("钟精励");            Request *request = new Request();            request->setRequestType("加薪");            request->setRequestContent("小菜请求加薪");            request->setNumber(1000);            jinli->GetResult(manager, *request);            zongjian->GetResult(chief_inspector, *request);            zhongjingli->GetResult(president, *request);            Request *request2 = new Request();            request2->setRequestType("请假");            request2->setRequestContent("小菜请假");            request2->setNumber(3);            jinli->GetResult(manager, *request2);            zongjian->GetResult(chief_inspector, *request2);            zhongjingli->GetResult(president, *request2);                        return 0;         }        


     2)改进后的代码

           说明:C++中不可以直接声明类的对象,但是可以直接声明类的指针。

#include <iostream>using namespace std; //enum  ManagerLevel{ "经理","总监","总经理"} ManagerLevel;  enum  ManagerLevel{ manager,chief_inspector,president} ;        //申请    class Request    {        //申请类别        private: string requestType;        public: string getRequestType()        {            return requestType;         }         void setRequestType(string value)  {     requestType = value;          }        //申请内容        private: string requestContent;        public: string getRequestContent()        {             return requestContent;         }          void  setRequestContent(string value)   {      requestContent = value;    }                //数量        private: int number;        public: int getNumber() { return number;  }  void setNumber(int value)  {  this->number = value;  }    };     //管理者  class Manager  {        protected: string name;        //管理者的上级         Manager *superior;        public: Manager(string name)        {            this->name = name;        }        //设置管理者的上级        void SetSuperior(Manager *superior)        {            this->superior = superior;        }        //申请请求        virtual void RequestApplications(Request request)        {}     };     //经理    class CommonManager :public Manager    {        public: CommonManager(string name)            : Manager(name)        { }         void RequestApplications(Request request)        {            if (request.getRequestType() == "请假" && request.getNumber() <= 2)            {                cout<<name<< request.getRequestContent()<<"数量"<< request.getNumber()<<"被批准"<<endl;             }            else            {                if (superior != NULL)                    superior->RequestApplications(request);            }        }    };     //总监    class Majordomo :public Manager    {        public:  Majordomo(string name)            : Manager(name)        { }         void RequestApplications(Request request)        {            if (request.getRequestType() == "请假" && request.getNumber() <= 5)            {                cout<<name<< request.getRequestContent()<<"数量"<< request.getNumber()<<"被批准"<<endl;             }            else            {                if (superior != NULL)                    superior->RequestApplications(request);            }        }    };     //总经理    class GeneralManager :public Manager    {        public: GeneralManager(string name): Manager(name)        { }        void RequestApplications(Request request)        {            if (request.getRequestType() == "请假")            {                cout<<name<< request.getRequestContent()<<"数量"<< request.getNumber()<<"被批准"<<endl;             }            else if (request.getRequestType() == "加薪" && request.getNumber() <= 500)            {               cout<<name<< request.getRequestContent()<<"数量"<< request.getNumber()<<"被批准"<<endl;             }            else if (request.getRequestType() == "加薪" && request.getNumber() > 500)            {            cout<<name<< request.getRequestContent()<<"数量"<< request.getNumber()<<"再说吧"<<endl;                            }        }    };         int main()        {            CommonManager *jinli = new CommonManager("金利");            Majordomo *zongjian = new Majordomo("宗剑");            GeneralManager *zhongjingli = new GeneralManager("钟精励");            jinli->SetSuperior(zongjian);            zongjian->SetSuperior(zhongjingli);            Request *request = new Request();            request->setRequestType("请假");            request->setRequestContent("小菜请假");            request->setNumber(1);            jinli->RequestApplications(*request);            Request *request2 = new Request();            request2->setRequestType("请假");            request2->setRequestContent("小菜请假");            request2->setNumber(4);            jinli->RequestApplications(*request2);            Request *request3 = new Request();            request3->setRequestType("加薪");            request3->setRequestContent("小菜请求加薪");            request3->setNumber(500);            jinli->RequestApplications(*request3);            Request *request4 = new Request();            request4->setRequestType("加薪");            request4->setRequestContent("小菜请求加薪");            request4->setNumber(1000);            jinli->RequestApplications(*request4);           return 0;         }

 

原创粉丝点击