职责链模式

以前的笔记,照抄了,理解应该是到位的.

又是多态,继承的直接应用。 职责链模式:使多个对象都有机会处理请求,从而避免请求的发送者和接收者之间的耦合关系。将这些对象连成一条链,并沿着这条链传递该请求,直到有一个对象处理它为止。

感觉很像 MFC 里的类关系,基类里一定有个基类指针.MFC 里好像是 static 指针.继承者把这个基类指针 base 指向自己的上一层次的类.虚函数 vfun()通过下面的方式实现调用链: base 可以是同一个层次的也可以是不同层次的,怎么链接对象。

vfunc() { xxx; return base->vfunc();}

例子:

#include <iostream>
using namespace std;
class Ojbect {
    public:
        virtual void click() = 0;
        virtual int show() = 0;
        virtual void process(int lev) = 0;
        virtual ~Ojbect(){}
        Ojbect* base;
        void setUpperPtr(Ojbect * b) {base = b;}
};

class View :public Ojbect{
    public:
        void click(){cout << "View click\n";}
        int show(){cout << "View show\n"; return 0;}
        void process(int lev) {
            if(lev < 5) {
                cout << "View handle process lvl < 5\n";
            }
        }
        virtual ~View(){}
};

class MessageBox :public View{
    public:
        void click(){cout << "MessageBox click\n"; base->click();}
        int show(){cout << "MessageBox show\n"; return View::show();}
        void process(int lev) {
            if(lev > 5 && lev < 10) {
                cout << "MessageBox handle process  5 < lvl < 10\n";
            } else {
                //View::process(lev);
                base->process(lev);
            }
        }
        virtual ~MessageBox(){}
};

class PushMessageBox :public MessageBox{
    public:
        void click(){cout << "PushMessageBox click\n";
            if(base) base->click();}
        int show(){cout << "PushMessageBox show\n"; return MessageBox::show();}
        void process(int lev) {
            if(lev > 10 && lev < 100) {
                cout << "PushMessageBox handle process  10 < lvl < 100\n";
            } else {
                //MessageBox::process(lev);
                base->process(lev);
            }
        }
        virtual ~PushMessageBox(){}
};

int main(int argc , char* argv[])
{
    PushMessageBox pushBox;
    MessageBox msgBox;
    View view;
    //指针可灵活,也可以跳这层次的指向view
    pushBox.setUpperPtr(&msgBox);
    msgBox.setUpperPtr(&view);
    pushBox.click();
    //也可以指向同一层次的类
    PushMessageBox pb1,pb2,pb3,pb4;
    pb1.setUpperPtr(&pb2);
    pb2.setUpperPtr(&pb3);
    pb3.setUpperPtr(&pb4);
    //循环成链...
    //pb4.setUpperPtr(&pb1);
    pb1.click();
    //强制层次关系,跟基类指针无关
    pushBox.show();
    //把判断条件放在虚函数里
    pushBox.process(20);
    pushBox.process(8);
    pushBox.process(3);

    return 0;
}

结果:

PushMessageBox click                                                                                                      [0/399]
MessageBox click
View click
PushMessageBox click
PushMessageBox click
PushMessageBox click
PushMessageBox click
PushMessageBox show
MessageBox show
View show
PushMessageBox handle process  10 < lvl < 100
MessageBox handle process  5 < lvl < 10
View handle process lvl < 5