设计模式——行为型模式(一)

行为模式涉及到算法和对象间职责的分配。行为模式不仅描述对象或类的模式,还描述他们之间的通信模式,这些模式刻画了在运行时难以跟踪的复杂的控制流。 
    行为类模式使用继承机制在类间分派行为;行为对象模式使用对象复合而不是继承。 
1. TemplateMethod——类行为模式 
作用: 
定义一个操作中算法的骨架,而将一些步骤延迟到子类中。TemplateMethod使得子类可以不改变一个算法的结构即可重定义该算法的某些特定步骤。

UML结构图: 

抽象基类: 
AbstractClass 定义算法的轮廓

解析: 
TemplateMethod的关键在于基类中定义了一个算法的轮廓,但是算法每一步具体的实现留给了派生类。这样也会造成设计的灵活性不高的缺点,因为轮廓已经定下来了想要改变就困难了,这也是为什么优先使用组合而不是继承的原因。

实现:

typedef string STATE;
class Flyweight
{
public:
    virtual ~Flyweight(){}
    STATE GetIntrinsicState()
    {
        return m_State;
    }
    virtual void Operation(STATE& ExtrinsincState)=0;
protected:
    Flyweight(const STATE& state):m_State(state){}
private:
    STATE m_State;
};

class ConcreteFlyweight:public Flyweight
{
public:
    ConcreteFlyweight(const STATE& state):Flyweight(state){}
    virtual ~ConcreteFlyweight(){}
    virtual void Operation(STATE& ExtrinsicState){}
};

class FlyweightFactory
{
public:
    FlyweightFactory(){}
    ~FlyweightFactory()
    {
        list<Flyweight*>::iterator iter1,iter2,temp;
        for(iter1=m_listFlyweight.begin(),iter2=m_listFlyweight.end();
        iter1!=iter2;)
        {
            temp = iter1;
            ++iter1;
            delete (*temp);
        }
        m_listFlyweight.clear();
    }
Flyweight* GetFlyweight(const STATE& key)
{
    list<Flyweight*>::iterator iter1,iter2;
    for(iter1=m_listFlyweight.begin(),iter2=m_listFlyweight.end();
    iter1!=iter2;++iter1)
    {
        if((*iter1)->GetIntrinsicState()==key)
        {
            cout<<"The Flyweight:"<<key<<"already exists"<<endl;
            return (*iter1);
        }
        cout<<"Creating a new Flyweight:"<<key<<endl;
        Flyweight* flyweight = new ConcreteFlyweight(key);
        m_listFlyweight.push_back(flyweight);
    }
}
private:
    list<Flyweight*> m_listFlyweight;
};

int main()
{
    FlyweightFactory* fly = new FlyweightFactory();
    fly->GetFlyweight("hello");
    fly->GetFlyweight("world");
    fly->GetFlyweight("hello");
    return 0;
}

2. Chain of responsibility——对象行为型模式 
作用: 
使多个对象都有机会处理请求,从而避免请求的发送者和接收者之间的耦合关系,将这些对象连成一条链,并沿着这条链传递该请求,直到有一个对象处理它为止。

UML结构图: 

抽象基类: 
Handler 定义一个处理请求的接口,在图中这个接口就是HanleRequest函数,这个类同时有一个指向Handler对象的指针,指向后续的处理请求的对象(如果有的话)。

实现:

//抽象机类,定义一个处理请求的接口
class Handler
{
public:
    Handler(Handler* pSuccessor=NULL):m_pSuccessor(pSuccessor){}
    virtual ~Handler()
    {
        delete m_pSuccessor;
        m_pSuccessor = NULL;
    }
    //虚函数,由派生类实现
    virtual void HandlerRequest()=0;
protected:
    Handler* m_pSuccessor;
};

class ConcreteHandler1:public Handler
{
public:
    ConcreteHandler1(Handler* pSuccessor=NULL):Handler(pSuccessor){}
    virtual ~ConcreteHandler1(){}
    virtual void HandlerRequest()
    {
        if(NULL!=m_pSuccessor)
            m_pSuccessor->HandlerRequest();
        else
            cout<<"HandlerRequest by ConcreteHandler1"<<endl;
    }
};
class ConcreteHandler2:public Handler
{
public:
    ConcreteHandler2(Handler* pSuccessor=NULL):Handler(pSuccessor){}
    virtual ~ConcreteHandler2(){}
    virtual void HandlerRequest()
    {
        if(NULL!=m_pSuccessor)
            m_pSuccessor->HandlerRequest();
        else
            cout<<"HandlerRequest by ConcreteHandler2"<<endl;
    }
};
int main()
{
    Handler* p1 = new ConcreteHandler1();
    Handler* p2 = new ConcreteHandler2(p1);
    p2->HandlerRequest();
    delete p2;
    return 0;
}

3. Command——对象行为模式 
作用: 
将一个请求封装为一个对象,从而可用不同的请求对客户进行参数化;对请求排队或记录请求日志,以及支持可撤销的操作。

UML结构图: 

解析: 
Command模式的思想是把命令封装在一个类中,就是这里的Command基类,同时把接收对象也封装在一个类中即这里的Receiver类,由调用这个命令的类即Invoker类来调用。Command类的作用和面向过程的回调函数类似,采用Command模式解耦了命令的发出者和命令的执行者。

实现:

class Reciever
{
public:
    Reciever(){}
    ~Reciever(){}
    void Action()
    { cout<<"Reciever action ..."<<endl; }
};

class Command
{
public:
    virtual ~Command(){}
    virtual void Excute()=0;
protected:
    Command(){}
};

class ConcreteCommand:public Command
{
public:
    ConcreteCommand(Reciever* rev)
    { this->_rev = rev; }
    ~ConcreteCommand()
    {}
    void Excute()
    {
        if(NULL!=_rev)
            _rev->Action();
        cout<<"ConcreteCommand.."<<endl;
    }
private:
    Reciever* _rev;
};

class Invoker
{
public:
    Invoker(Command* cmd)
    { _cmd = cmd; }
    ~Invoker()
    { delete _cmd; }
    void Invoke()
    { _cmd->Excute(); }
private:
    Command* _cmd;
};

int main()
{
    Reciever* rev = new Reciever();
    Command* cmd = new ConcreteCommand(rev);
    Invoker* inv = new Invoker(cmd);
    inv->Invoke();
    delete inv;
    return 0;
}

4. Observer——对象行为型模式 
作用: 
定义对象间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并被自动更新。

UML结构图: 

解析: 
Observer模式定义的是一对多(一个Subject对多个Observer)关系,当Subject类的状态发生变化的时候通知与之对应的Observer类们也去相应的更新状态,同时支持动态的添加和删除Observer对象的功能。 
Observer模式的实现要点是,第一一般Subject类都是采用链表等容器来存放Observer对象,第二抽出Observer对象的而一些公共的属性形成Observer基类,而Subject中保存的则是Observer类对象的指针,这样就使Subject和具体的Observer实现了解耦,即Subject不需要关心具体是哪个Observer放进了自己的容器。

实现:

typedef int STATE;
class Subject;
//Observer抽象基类
class Observer
{
public:
    Observer():m_nObserverState(-1){}
    virtual ~Observer(){}
    //纯虚函数,各个派生类可能有不同的实现
    //通知Observer状态发生了改变
    virtual void Update(Subject* pSubject)=0;
protected:
    STATE m_nObserverState; //模拟保存Observer状态的变量
};

//Subject抽象基类,只需要知道Observer基类的声明就可以了
class Subject
{
public:
    Subject():m_nSubjectState(-1){}
    virtual ~Subject()
    {
        list<Observer*>::iterator iter1,iter2,temp;
        for(iter1=m_ListObserver.begin(),iter2=m_ListObserver.end();
        iter1!=iter2;)
        {
            temp = iter1;
            ++iter1;
            delete (*temp);
        }
        m_ListObserver.clear();
    }
    void Notify() //通知对象改变状态
    {
        cout<<"Notify Observer‘s State"<<endl;
        list<Observer*>::iterator iter1,iter2;
        for(iter1=m_ListObserver.begin(),iter2=m_ListObserver.end();
        iter1!=iter2;++iter1)
            (*iter1)->Update(this);
        }
    }
    void Attach(Observer* pObserver) //新增对象
    {
        cout<<"Attach an Observer"<<endl;
        m_ListObserver.push_back(pObserver);
    }
    void Detach(Observer* pObserver) // 删除对象
    {
        list<Observer*>::iterator iter;
        iter = find(m_ListObserver.begin(),m_ListObserver.end(),pObserver);
        if(m_ListObserver.end()!=iter)
        m_ListObserver.erase(iter);
        cout<<"Detach an Observer"<<endl;
    }
    //虚函数,提供默认的实现,派生类可以自己实现来覆盖基类的实现
    virtual void SetState(STATE nState) //设置状态
    {
        cout<<"SetState by Subject"<<endl;
        m_nSubjectState = nState;
    }
    virtual STATE GetState() //得到状态
    {
        cout<<"GetState by Subject"<<endl;
        return m_nSubjectState;
    }
protected:
    STATE m_nSubjectState; //模拟保存Subject状态的变量
    list<Observer*> m_ListObserver; //保存Observer指针的链表
};

//ConcreteSubject类,派生自Subject类
class ConcreteSubject:public Subject
{
public:
    ConcreteSubject():Subject(){}
    virtual ~ConcreteSubject(){}
    //派生类自己实现来覆盖基类的实现
    virtual void SetState(STATE nState) //设置状态
    {
        cout<<"SetState by ConcreteSubject"<<endl;
        m_nSubjectState = nState;
    }
    virtual STATE GetState() //得到状态
    {
        cout<<"GetState by ConcreteSubject"<<endl;
        return m_nSubjectState;
    }
};

//ConcreteObserver类派生自Observer类
class ConcreteObserver:public Observer
{
public:
    ConcreteObserver():Observer(){}
    virtual ~ConcreteObserver(){}
    //虚函数,实现基类提供的接口
    virtual void Update(Subject* pSubject)
    {
        if(NULL==pSubject)
            return;
        m_nObserverState = pSubject->GetState();
        cout<<"The OberverState is"<<m_nObserverState<<endl;
    }
};
int main()
{
    Observer* p1 = new ConcreteObserver;
    Observer* p2 = new ConcreteObserver;
    Subject* p = new ConcreteSubject;
    p->Attach(p1);
    p->Attach(p2);
    p->SetState(4);
    p->Notify();
    p->Detach(p1);
    p->SetState(10);
    p->Notify();
    delete p;
    return 0;
}

5. Strategy——对象行为型模式 
作用: 
定义一系列的算法,把他们一个个封装起来,并且使它们可以相互替换。本模式使得算法可独立于使用它的客户而变化。

UML结构图: 

解析: 
Strategy模式是对算法的封装,处理一个问题的时候可能有多种算法,这些算法的接口(输入参数、输出参数)都是一致的,那么可以考虑采用Strategy模式对这些算法进行封装,在基类中定义一个函数接口即可。

实现:

class Strategy
{
public:
    virtual ~Strategy(){}
    virtual void AlgorithmInterface()=0;
};

class ConcreteStrategyA:public Strategy
{
public:
    virtual ~ConcreteStrategyA(){}
    virtual void AlgorithmInterface()
    { cout<<"AlgorithmInterface Implemented by ConcreteStrategyA"<<endl; }
};

class Context
{
public:
    Context(Strategy* pStrategy):m_pStrategy(pStrategy){}
    ~Context()
    {
        delete m_pStrategy;
        m_pStrategy = NULL;
    }
    void ContextInterface()
    {
        if(NULL!=m_pStrategy)
            m_pStrategy->AlgorithmInterface();
    }
private:
    Strategy* m_pStrategy;
};
int main()
{
    Strategy* pStrategy = new ConcreteStrategyA();
    Context* pContext = new Context(pStrategy);
    pContext->ContextInterface();
    delete pContext;
    return 0;
}
时间: 2024-10-13 11:36:08

设计模式——行为型模式(一)的相关文章

JDK 源码 阅读 - 2 - 设计模式 - 创建型模式

A.创建型模式 抽象工厂(Abstract Factory) javax.xml.parsers.DocumentBuilderFactory DocumentBuilderFactory通过FactoryFinder实例化具体的Factory. 使用例子: DocumentBuilderFactory docBuilderFactory = DocumentBuilderFactory.newInstance(); DocumentBuilder docBuilder = docBuilder

设计模式——创建型模式

简单的说我们可以把23种设计模式可以归为三大类,分别是创建型模式.结构型模式和行为型模式. 今天,首先看一下创建型模式.创建型设计模式包括5种:单例模式(Singleton).工厂方法模式(Factory Method).抽象工厂模式(Abstract Factory).建造者模式(Builder).原型模式(Prototype).  1.单例模式(Singleton)        1)简介 保证一个类仅有一个实例,并提供一个访问它的全局访问点. 单例模式是一种常用的软件设计模式.在它的核心结

设计模式06-原型模式

1. 概念 用原型的实例指定创建对象的种类,并且通过拷贝这些原型对象来创建新的对象   在java中直接实现Cloneable接口即可 2. 案例 /********************************************************************** * <pre> * FILE : PrototypeDemo.java * CLASS : PrototypeDemo * * AUTHOR : Liaokailin * * FUNCTION : TODO

C#设计模式-创建型模式(转)

一.简单工厂模式 简单工厂模式Simple Factory,又称静态工厂方法模式.它是类的创建模式.是由一个工厂对象决定创建出哪一种产品类的实例,是不同的工厂方法模式的一个特殊实现. 优点: u 模式的核心是工厂类,该类中含有必要的判断逻辑,可以决定在什么时候创建哪一个产品类的实例,客户端可以免除直接创建产品对象的责任,而仅仅负责"消费"产品. u 简单工厂模式实现了对责任的分割. 缺点: u 当产品类有复杂的多层次等级结构时,工厂类只有它自己.以不变应万变. u 模式中工厂类集中了所

【C#设计模式——创建型模式】抽象工厂模式

抽象工厂模式比工厂模式具有更高层次的抽象性.当要返回一系列相关类中的某一个,而每个类都能根据需要返回不同的对象时,可以选择这种模式.直接进入示例. 示例描述:完成花园的规划,多种花园种类,每个里面多种植物 编写一个基类Garden,Garden就是抽象工厂.它定义了具体类中的方法,并返回一系列相关类中的某个类. public class Garden { protected Plant center, shade, border; protected bool showCenter, showS

设计模式——行为型模式

继<设计模式--创建型模式>和<设计模式--结构型模式>之后,今天介绍一下行为型模式. 行为模式设计到算法和对象间的职责分配,不仅描述对象或类的模式,还描述他们之间的通信方式,客服了运行时难以跟踪的复杂的控制流,他们将你的注意力重控制流转移到对象间的关系上来.行为类模式采用继承机制在类间分派行为,例:模板方法模式.解释器模式:行为对象模式描述了一组相互对等的对象如何相互协作以完成其中任何一个对象都单独无法完成的任务,例:中介者模式.职责链模式.策略模式:其它的行为对象模式常将行为封

java设计模式--行为型模式--迭代模式

1 迭代器模式 2 概述 3 给定一个语言,定义它的文法的一种表示,并定义一个解释器,这个解释器使用该表示来解释语言中的句子. 4 5 6 适用性 7 1.访问一个聚合对象的内容而无需暴露它的内部表示. 8 9 2.支持对聚合对象的多种遍历. 10 11 3.为遍历不同的聚合结构提供一个统一的接口(即,支持多态迭代). 12 13 14 参与者 15 1.Iterator 16 迭代器定义访问和遍历元素的接口. 17 18 2.ConcreteIterator 19 具体迭代器实现迭代器接口.

java设计模式--行为型模式--命令模式

1 命令模式 2 概述 3 将一个请求封装为一个对象,从而使你可用不同的请求对客户进行参数化:对请求排队或记录请求日志,以及支持可撤消的操作. 4 5 6 适用性 7 1.抽象出待执行的动作以参数化某对象. 8 9 2.在不同的时刻指定.排列和执行请求. 10 11 3.支持取消操作. 12 13 4.支持修改日志,这样当系统崩溃时,这些修改可以被重做一遍. 14 15 5.用构建在原语操作上的高层操作构造一个系统. 16 17 18 参与者 19 1.Command 20 声明执行操作的接口.

【C#设计模式——创建型模式】工场方法模式

工场方法模式对简单工场模式进行了乔庙的扩展,不是用一个专门的类来决定实例化哪一个子类.相反,超类把这种决定延迟到每个子类.这种模式实际上没有决策点,就是没有直接选择一个子类实例化的决策. 看书上的例子有点复杂,自己写了一个简单例子: 示例目标:对数组进行定向排序 基类FormatList对指定数组进行排序,具体实现交给子类实现 public abstract class FormatList { public int[] result; protected abstract void Forma

设计模式---创建型模式

一.概况 总体来说设计模式分为三大类: (1)创建型模式,共五种:工厂方法模式.抽象工厂模式.单例模式.建造者模式.原型模式. (2)结构型模式,共七种:适配器模式.装饰器模式.代理模式.外观模式.桥接模式.组合模式.享元模式. (3)行为型模式,共十一种:策略模式.模板方法模式.观察者模式.迭代子模式.责任链模式.命令模式.备忘录模式.状态模式.访问者模式.中介者模式.解释器模式. 二.设计模式的六大原则 1.开闭原则(Open Close Principle) 开闭原则就是说对扩展开放,对修