访问者模式.cpp
# include <iostream>
# include <list>
# include <memory>
using namespace std;
namespace ns1
{ class Medicine { public : virtual ~ Medicine ( ) { } virtual string getMdcName ( ) const = 0 ; virtual float getPrice ( ) const = 0 ; } ; class M_asplcrp : public Medicine { public : string getMdcName ( ) const override { return "Aspirin enteric-coated tablets" ; } float getPrice ( ) const override { return 46.8f ; } } ; class M_fftdnhsp : public Medicine { public : string getMdcName ( ) const override { return "Fluvastatin sodium sustained-release tablets" ; } float getPrice ( ) const override { return 111.3f ; } } ; class M_dlx : public Medicine { public : string getMdcName ( ) const override { return "Deanxit" ; } float getPrice ( ) const override { return 122.0f ; } } ; class MedicineProc { list< shared_ptr< Medicine>> m_mdclist; public : void addMedicine ( const shared_ptr< Medicine> & p_mdc) { m_mdclist. push_back ( p_mdc) ; } void procAction ( const string & strvisitor) { if ( strvisitor == "Toll collector" ) { float totalcost = 0.0f ; for ( auto iter = m_mdclist. begin ( ) ; iter != m_mdclist. end ( ) ; ++ iter) { float tmpprice = ( * iter) -> getPrice ( ) ; totalcost += tmpprice; cout << "yao: " << ( * iter) -> getMdcName ( ) << ", price: " << tmpprice << endl; } cout << "total price: " << totalcost << ", Toll collector charges a fee!" << endl; } else if ( strvisitor == "Drug taking personnel" ) for ( auto iter = m_mdclist. begin ( ) ; iter != m_mdclist. end ( ) ; ++ iter) cout << "Drug taking personnel give " << ( * iter) -> getMdcName ( ) << " to me!" << endl; else if ( strvisitor == "dietitian" ) cout << "Nutritionist suggested: match coarse grains with staple foods and eat meat properly!" << endl; else if ( strvisitor == "Fitness coach" ) cout << "The fitness coach suggested: do more aerobic exercises such as jogging (35 minutes), warm up before and after jogging, avoid anxiety, avoid staying up late, and take a bed rest before 22:30!" << endl; } } ;
} namespace ns2
{ class Visitor ; class Medicine { public : virtual ~ Medicine ( ) { } virtual void Accept ( shared_ptr< Visitor> & pvisitor) = 0 ; public : virtual string getMdcName ( ) = 0 ; virtual float getPrice ( ) = 0 ; } ; class M_asplcrp : public Medicine { public : string getMdcName ( ) override { return "Aspirin enteric-coated tablets" ; } float getPrice ( ) override { return 46.8f ; } public : void Accept ( shared_ptr< Visitor> & pvisitor) override ; } ; class M_fftdnhsp : public Medicine { public : string getMdcName ( ) override { return "Fluvastatin sodium sustained-release tablets" ; } float getPrice ( ) override { return 111.3f ; } public : void Accept ( shared_ptr< Visitor> & pvisitor) override ; } ; class M_dlx : public Medicine { public : string getMdcName ( ) override { return "Deanxit" ; } float getPrice ( ) override { return 122.0f ; } public : void Accept ( shared_ptr< Visitor> & pvisitor) override ; } ; class Visitor { public : virtual ~ Visitor ( ) { } virtual void Visit_elm_asplcrp ( M_asplcrp * pelem) = 0 ; virtual void Visit_elm_fftdnhsp ( M_fftdnhsp * pelem) = 0 ; virtual void Visit_elm_dlx ( M_dlx * pelem) = 0 ; } ; class Visitor_SFRY : public Visitor { float m_totalcost = 0.0f ; public : void Visit_elm_asplcrp ( M_asplcrp * pelem) override { float tmpprice = pelem-> getPrice ( ) ; cout << "yao: " << pelem-> getMdcName ( ) << ", price: " << tmpprice << endl; m_totalcost += tmpprice; } void Visit_elm_fftdnhsp ( M_fftdnhsp * pelem) override { float tmpprice = pelem-> getPrice ( ) ; cout << "yao: " << pelem-> getMdcName ( ) << ", price: " << tmpprice << endl; m_totalcost += tmpprice; } void Visit_elm_dlx ( M_dlx * pelem) override { float tmpprice = pelem-> getPrice ( ) ; cout << "yao: " << pelem-> getMdcName ( ) << ", price: " << tmpprice << endl; m_totalcost += tmpprice; } float getTotalCost ( ) const { return m_totalcost; } } ; class Visitor_QYRY : public Visitor { public : void Visit_elm_asplcrp ( M_asplcrp * pelem) override { cout << "Drug taking personnel give " << pelem-> getMdcName ( ) << " to me!" << endl; } void Visit_elm_fftdnhsp ( M_fftdnhsp * pelem) override { cout << "Drug taking personnel give " << pelem-> getMdcName ( ) << " to me!" << endl; } void Visit_elm_dlx ( M_dlx * pelem) override { cout << "Drug taking personnel give " << pelem-> getMdcName ( ) << " to me!" << endl; } } ; class Visitor_YYS : public Visitor { public : void Visit_elm_asplcrp ( M_asplcrp * pelem) override { cout << "The nutritionist suggested: Eating more coarse grains and less oil can effectively prevent blood clots!" << endl; } void Visit_elm_fftdnhsp ( M_fftdnhsp * pelem) override { cout << "The nutritionist suggested: Eating more mushrooms, onions, and kiwifruit can effectively reduce blood lipids!" << endl; } void Visit_elm_dlx ( M_dlx * pelem) override { cout << "The nutritionist suggested: Go out more to breathe fresh air, get more sunshine, go to more crowded places, and keep an optimistic and cheerful mood!" << endl; } } ; void M_asplcrp :: Accept ( shared_ptr< Visitor> & pvisitor) { pvisitor-> Visit_elm_asplcrp ( this ) ; } void M_fftdnhsp :: Accept ( shared_ptr< Visitor> & pvisitor) { pvisitor-> Visit_elm_fftdnhsp ( this ) ; } void M_dlx :: Accept ( shared_ptr< Visitor> & pvisitor) { pvisitor-> Visit_elm_dlx ( this ) ; } class ObjectStructure { list< shared_ptr< Medicine>> m_mdclist; public : void addMedicine ( const shared_ptr< Medicine> & p_mdc) { m_mdclist. push_back ( p_mdc) ; } void procAction ( shared_ptr< Visitor> & pvisitor) { for ( auto iter = m_mdclist. begin ( ) ; iter != m_mdclist. end ( ) ; ++ iter) ( * iter) -> Accept ( pvisitor) ; } } ;
} namespace ns3
{ class Medicine ; class Visitor { public : virtual ~ Visitor ( ) { } virtual void Visit ( Medicine * const pelem) = 0 ; } ; class Medicine { public : virtual ~ Medicine ( ) { } virtual void Accept ( shared_ptr< Visitor> & pvisitor) { pvisitor-> Visit ( this ) ; } public : virtual string getMdcName ( ) const = 0 ; virtual float getPrice ( ) const = 0 ; } ; class M_asplcrp : public Medicine { public : string getMdcName ( ) const override { return "Aspirin enteric-coated tablets" ; } float getPrice ( ) const override { return 46.8f ; } } ; class M_fftdnhsp : public Medicine { public : string getMdcName ( ) const override { return "Fluvastatin sodium sustained-release tablets" ; } float getPrice ( ) const override { return 111.3f ; } } ; class M_dlx : public Medicine { public : string getMdcName ( ) const override { return "Deanxit" ; } float getPrice ( ) const override { return 122.0f ; } } ; class Visitor_SFRY : public Visitor { float m_totalcost = 0.0f ; public : void Visit ( Medicine * const m) override { float tmpprice = m-> getPrice ( ) ; m_totalcost += tmpprice; cout << "yao: " << m-> getMdcName ( ) << ", price: " << tmpprice << endl; } float getTotalCost ( ) const { return m_totalcost; } } ; class Visitor_QYRY : public Visitor { public : void Visit ( Medicine * const m) override { cout << "Drug taking personnel give " << m-> getMdcName ( ) << " to me!" << endl; } } ; class Visitor_YYS : public Visitor { public : void Visit ( Medicine * const m) override { cout << "The nutritionist suggested: Eating more coarse grains and less oil can effectively prevent blood clots!" << endl; cout << "The nutritionist suggested: Eating more mushrooms, onions, and kiwifruit can effectively reduce blood lipids!" << endl; cout << "The nutritionist suggested: Go out more to breathe fresh air, get more sunshine, go to more crowded places, and keep an optimistic and cheerful mood!" << endl; } } ; class ObjectStructure { list< shared_ptr< Medicine>> m_mdclist; public : void addMedicine ( const shared_ptr< Medicine> & p_mdc) { m_mdclist. push_back ( p_mdc) ; } void procAction ( shared_ptr< Visitor> & pvisitor) { for ( auto iter = m_mdclist. begin ( ) ; iter != m_mdclist. end ( ) ; ++ iter) ( * iter) -> Accept ( pvisitor) ; } } ;
} int main ( )
{
# if 0 using namespace ns1; shared_ptr< Medicine> pm1 ( new M_asplcrp ( ) ) ; shared_ptr< Medicine> pm2 ( new M_fftdnhsp ( ) ) ; shared_ptr< Medicine> pm3 ( new M_dlx ( ) ) ; MedicineProc mdcprocobj; mdcprocobj. addMedicine ( pm1) ; mdcprocobj. addMedicine ( pm2) ; mdcprocobj. addMedicine ( pm3) ; mdcprocobj. procAction ( "Toll collector" ) ; mdcprocobj. procAction ( "Drug taking personnel" ) ;
# endif # if 1 using namespace ns3; shared_ptr< Medicine> mdc_asplcrp ( new M_asplcrp ( ) ) ; shared_ptr< Medicine> mdc_fftdnhsp ( new M_fftdnhsp ( ) ) ; shared_ptr< Medicine> mdc_dlx ( new M_dlx ( ) ) ; shared_ptr< Visitor> visitor_sf ( new Visitor_SFRY ( ) ) ; mdc_asplcrp-> Accept ( visitor_sf) ; mdc_fftdnhsp-> Accept ( visitor_sf) ; mdc_dlx-> Accept ( visitor_sf) ; cout << "total price: " << dynamic_pointer_cast < Visitor_SFRY> ( visitor_sf) -> getTotalCost ( ) << ", the toll collector charged me!" << endl; shared_ptr< Visitor> visitor_qy ( new Visitor_QYRY ( ) ) ; mdc_asplcrp-> Accept ( visitor_qy) ; mdc_fftdnhsp-> Accept ( visitor_qy) ; mdc_dlx-> Accept ( visitor_qy) ; shared_ptr< Visitor> visitor_yys ( new Visitor_YYS ( ) ) ; mdc_asplcrp-> Accept ( visitor_yys) ; mdc_fftdnhsp-> Accept ( visitor_yys) ; mdc_dlx-> Accept ( visitor_yys) ; shared_ptr< ObjectStructure> objstruc ( new ObjectStructure ( ) ) ; objstruc-> addMedicine ( mdc_asplcrp) ; objstruc-> addMedicine ( mdc_fftdnhsp) ; objstruc-> addMedicine ( mdc_dlx) ; objstruc-> procAction ( visitor_yys) ;
# endif cout << "Over!\n" ; return 0 ;
}