直通通道:设计模式(一)
装饰器模式
#include <iostream>
// 普通员工有销售奖金,累计奖金,部门经理除此之外还有团队奖金;后面可能会添加环比增长奖金,同时可能产生不同的奖金组合;
// 销售奖金 = 当月销售额 * 4%
// 累计奖金 = 总的回款额 * 0.2%
// 部门奖金 = 团队销售额 * 1%
// 环比奖金 = (当月销售额-上月销售额) * 1%
// 销售后面的参数可能会调整
using namespace std;
class Context {
public:
bool isMgr;
// User user;
// double groupsale;
};
// 试着从职责出发,将职责抽象出来
class CalcBonus {
public:
CalcBonus(CalcBonus * c = nullptr) : cc(c) {}
virtual double Calc(Context &ctx) {
return 0.0; // 基本工资
}
virtual ~CalcBonus() {}
protected:
CalcBonus* cc;
};
class CalcMonthBonus : public CalcBonus {
public:
CalcMonthBonus(CalcBonus * c) : CalcBonus(c) {}
virtual double Calc(Context &ctx) {
double mbonus /*= 计算流程忽略*/;
return mbonus + cc->Calc(ctx); //加上基类(基本工资)
}
};
class CalcSumBonus : public CalcBonus {
public:
CalcSumBonus(CalcBonus * c) : CalcBonus(c) {}
virtual double Calc(Context &ctx) {
double sbonus /*= 计算流程忽略*/;
return sbonus + cc->Calc(ctx);
}
};
class CalcGroupBonus : public CalcBonus {
public:
CalcGroupBonus(CalcBonus * c) : CalcBonus(c) {}
virtual double Calc(Context &ctx) {
double gbnonus /*= 计算流程忽略*/;
return gbnonus + cc->Calc(ctx);
}
};
class CalcCycleBonus : public CalcBonus {
public:
CalcCycleBonus(CalcBonus * c) : CalcBonus(c) {}
virtual double Calc(Context &ctx) {
double gbnonus /*= 计算流程忽略*/;
return gbnonus + cc->Calc(ctx);
}
};
int main() {
// 1. 普通员工
Context ctx1;
CalcBonus *base = new CalcBonus();
CalcBonus *cb1 = new CalcSumBonus(base);
CalcBonus *cb2 = new CalcMonthBonus(cb1);
cb2->Calc(ctx1);
// 2. 部门经理
Context ctx2;
CalcBonus *cb3 = new CalcGroupBonus(cb2);
cb3->Calc(ctx2);
}
// 能不能用 功能链的写法 来实现 装饰器功能?
// 可以
组合模式
责任链模式
#include <string>
class Context {
public:
std::string name;
int day;
};
//抽象出一个接口
class IHandler {
public:
virtual ~IHandler() {}
void SetNextHandler(IHandler *next) { //链表关系
next = next;
}
bool Handle(const Context &ctx) { //具体传递流程
if (CanHandle(ctx)) {
return HandleRequest(ctx);
} else if (GetNextHandler()) {
return GetNextHandler()->HandleRequest(ctx);
} else {
// err
}
return false; //打断链条
}
protected:
virtual bool HandleRequest(const Context &ctx) = 0;
virtual bool CanHandle(const Context &ctx) =0;
IHandler * GetNextHandler() {
return next;
}
private:
IHandler *next; //组合基类指针
};
//能不能处理,以及怎么处理
class HandleByMainProgram : public IHandler { //小组长
protected:
virtual bool HandleRequest(const Context &ctx){
//
return true;
}
virtual bool CanHandle(const Context &ctx) {
//
return true;
}
};
class HandleByProjMgr : public IHandler { //项目经理
protected:
virtual bool HandleRequest(const Context &ctx){
//
return true;
}
virtual bool CanHandle(const Context &ctx) {
//
return true;
}
};
class HandleByBoss : public IHandler { //老板
protected:
virtual bool HandleRequest(const Context &ctx){
//
return true;
}
virtual bool CanHandle(const Context &ctx) {
//
return true;
}
};
class HandleByBeauty : public IHandler { //前台
protected:
virtual bool HandleRequest(const Context &ctx){
//
return true;
}
virtual bool CanHandle(const Context &ctx) {
//
return true;
}
};
int main() {
// IHandler * h1 = new HandleByMainProgram();
// IHandler * h2 = new HandleByProjMgr();
// IHandler * h3 = new HandleByBoss();
// h1->SetNextHandler(h2);
// h2->SetNextHandler(h3);
//处理流程前台->小组长->项目经理->老板
IHandler * h0 = new HandleByBeauty();
IHandler * h1 = new HandleByMainProgram();
IHandler * h2 = new HandleByProjMgr();
IHandler * h3 = new HandleByBoss();
h0->SetNextHandler(h1);
h1->SetNextHandler(h2);
h2->SetNextHandler(h3);
// 设置下一指针
Context ctx;
h0->Handle(ctx);
return 0;
}
}
模板方法
#include <iostream>
using namespace std;
class ZooShow {
public:
// 固定流程封装到这里
void Show() { //算法骨架
Show0();
Show1();
Show2();
Show3();
}
protected:
// 子流程 使用protected保护起来 不被客户调用 但允许子类扩展
virtual void Show0(){
cout << "show0" << endl;
}
virtual void Show2(){
cout << "show2" << endl;
}
virtual void Show1() {
}
virtual void Show3() {
}
};
class ZooShowEx : public ZooShow {
protected:
virtual void Show1(){
cout << "show1" << endl;
}
virtual void Show3(){
cout << "show3" << endl;
}
virtual void Show4() {
//
}
};
class ZooShowEx1 : public ZooShow {
protected:
virtual void Show0(){
cout << "show1" << endl;
}
virtual void Show2(){
cout << "show3" << endl;
}
};
class ZooShowEx2 : public ZooShow {
protected:
virtual void Show1(){
cout << "show1" << endl;
}
virtual void Show2(){
cout << "show3" << endl;
}
};
int main () {
ZooShow *zs = new ZooShowEx;
// ZooShow *zs1 = new ZooShowEx1;
// ZooShow *zs2 = new ZooShowEx2;
zs->Show();
return 0;
}
充电站
推荐一个零声学院免费公开课程,个人觉得老师讲得不错,分享给大家:Linux,Nginx,ZeroMQ,MySQL,Redis,fastdfs,MongoDB,ZK,流媒体,CDN,P2P,K8S,Docker,TCP/IP,协程,DPDK等技术内容,立即学习