C++实践::Template实现Observer模式

    技术2022-05-19  20

    转自:http://blog.csdn.net/yhjvc/archive/2005/11/25/536589.aspx

     

    C++ template实现的通用Observer代码。本文并无神秘之处,template只是运用在对状态信息类型的泛化。过多的细节就没必要不讲了,我想各位看官比我更明白吧

    /*

     

     

    Design Pattern implementation with C++ template - Observer

     

     

    */

     

     

    #ifndef _OBSERVER_H_

     

     

    #define _OBSERVER_H_

     

     

    #include<vector>

     

     

     

     

     

    template<typename Msg>

    struct helper;

     

     

     

    template<typename Msg>

    struct subject;

     

     

     

    template<typename Msg>

    class observer

    {

         friend class helper<Msg>;

    protected:

         observer():psbj_(NULL)

         {}

    public:    

         virtual ~observer()

    {

             if(psbj_)

                 psbj_->detach(*this);

    }

        

     

     

         virtual void update(const Msg&)=0;

    private:

         subject<Msg>* psbj_;

    };

     

     

     

    template<typename Msg>

    class subject

    {

         friend class helper<Msg>;

    public:

         virtual ~subject()

         {

             typename std::vector<observer<Msg>*>::iterator begin = obsvrvec_.begin();

             typename std::vector<observer<Msg>*>::iterator end = obsvrvec_.end();

            

             for(; begin!=end; ++begin)

                       helper<Msg>::attachtosubject(NULL, *begin);

         }

         void attach(observer<Msg>& rhs) //register

         {

               obsvrvec_.push_back(&rhs);

               helper<Msg>::attachtosubject(this, &rhs);

         }

     

     

     

         void detach(observer<Msg>& rhs) //unregister

         {

             typename std::vector<observer<Msg>*>::iterator matched = find(obsvrvec_.begin(), obsvrvec_.end(), &rhs);

             if(matched != obsvrvec_.end())

                 obsvrvec_.erase(matched);

         }

        

         void notify() //notify all observers

         {

             typename std::vector<observer<Msg>*>::iterator begin = obsvrvec_.begin();

             typename std::vector<observer<Msg>*>::iterator end = obsvrvec_.end();

            

             for(; begin!=end; ++begin)

                  (*begin)->update(message_);

         }

        

    protected:

         Msg& message()

            {   return message_; }

           

         const Msg& message() const

            {   return message_; }

           

         void message(const Msg& rhs)

            {  message_ = rhs; }

    private:

         Msg message_;

         std::vector<observer<Msg>*> obsvrvec_;

    };

     

     

     

    template<typename Msg>

    struct helper

    {

       static void attachtosubject(subject<Msg>* sbj, observer<Msg>* obsv)

           {   obsv->psbj_ = sbj;  }  

    };

    #endif //_OBSERVER_H_

     

     

     

     

     

    下面是应用的示例代码

    class ConcreteObserver1:public observer<string>

    {

    public:

        void update(const string& message)

            {  cout<<message<<endl;  }

    };

     

     

     

    class ConcreteObserver2:public observer<string>

    {

    public:

        void update(const string& message)

        {

            copy(message.rbegin(), message.rend(), ostream_iterator<string::value_type>(cout));

            cout<<endl;

        }

    };

     

     

     

    class ConcreteSubject:public subject<string>

    {

    public:

         void set(const string& str)

            {  message(str); }

    };

     

     

     

    int main()

    {

        ConcreteSubject subject;

        ConcreteObserver1 o1;

        ConcreteObserver2 o2;

        subject.attach(o1);

        subject.attach(o2);

        subject.set("show me the money");

        subject.notify();

    }


    最新回复(0)