本章要点
1. 知道OO基础,并不足以让你设计出良好的OO系统。2. 良好的OO设计必须具备可复用、可扩充、可维护三个特性。
3. 模式可以让我们建造具有良好OO设计质量的系统。
4. 模式被认为是历经验证的OO设计经验。
5. 模式不是代码,而是针对设计问题的通用解决方案。你可把它们应用到待定的应用中。
6. 模式不是发明,而是被发现。
7. 大多数的模式和原则,都着眼于软件变化的主题。
8. 大多数的模式都允许系统局部改变独立于其他部分。
9. 我们常把系统中会变化的部分抽出来封装。
10. 模式让开发人员之间有共享语言,能够最大化沟通的价值。
设计原则
1. 封装变化(找出应用中可能需要变化之处,把它们独立出来,不要和那些不需要变化的代码混在一起)。2. 多用组合,少用继承
3. 针对接口编程,不针对实现编程。
模式
策略模式:定义算法族,分别封装起来,让它们之间可以互相替换,此模式让算法的变化独立于使用算法的客户。UML图
书本案例UML图
源代码(C++)
#include <iostream>
using namespace std;
class FlyBehavior
{
public:
virtual void Fly() = 0;
};
class FlyWithWings: public FlyBehavior
{
public:
FlyWithWings(){}
virtual ~FlyWithWings(){}
virtual void Fly()
{
cout<<"I'm flying!!"<<endl;
}
};
class FlyNoWay:public FlyBehavior
{
public:
FlyNoWay(){}
virtual ~FlyNoWay(){}
virtual void Fly()
{
cout<<"I can't fly"<<endl;
}
};
class FlyRocketPowered:public FlyBehavior
{
public:
FlyRocketPowered(){}
virtual ~FlyRocketPowered(){}
virtual void Fly()
{
cout<<"I'm flying with a rocket"<<endl;
}
};
class QuackBehavior
{
public:
virtual void Quack() = 0;
};
class RealQuack:public QuackBehavior
{
public:
RealQuack(){}
virtual ~RealQuack(){}
virtual void Quack()
{
cout<<"Quack"<<endl;
}
};
class Squeak:public QuackBehavior
{
public:
Squeak(){}
virtual ~Squeak(){}
virtual void Quack()
{
cout<<"Squeak"<<endl;
}
};
class FakeQuack:public QuackBehavior
{
public:
FakeQuack(){}
virtual ~FakeQuack(){}
virtual void Quack()
{
cout<<"Qwak"<<endl;
}
};
class MuteQuack:public QuackBehavior
{
public:
MuteQuack(){}
virtual ~MuteQuack(){}
virtual void Quack()
{
cout<<"<< Silence >>"<<endl;
}
};
class Duck
{
public:
Duck(){}
virtual ~Duck()
{
flyBehavior = NULL;
quackBehavior = NULL;
}
virtual void Display() = 0;
void SetFlyBehavior (FlyBehavior* fb)
{
flyBehavior = fb;
}
void SetQuackBehavior(QuackBehavior* qb)
{
quackBehavior = qb;
}
void PerformFly()
{
flyBehavior->Fly();
}
void PerformQuack()
{
quackBehavior->Quack();
}
void Swim()
{
cout<<"All ducks float, even decoys!"<<endl;
}
private:
FlyBehavior* flyBehavior;
QuackBehavior* quackBehavior;
};
class MallardDuck:public Duck
{
public:
MallardDuck()
{
SetQuackBehavior(new RealQuack());
SetFlyBehavior(new FlyWithWings());
}
virtual ~MallardDuck(){}
virtual void Display()
{
cout<<"I'm a real Mallard duck."<<endl;
}
};
class RedHeadDuck:public Duck
{
public:
RedHeadDuck()
{
SetFlyBehavior(new FlyWithWings());
SetQuackBehavior(new RealQuack());
}
virtual ~RedHeadDuck(){}
virtual void Display()
{
cout<<"I'm a real Red Headed duck."<<endl;
}
};
class RubberDuck:public Duck
{
public:
RubberDuck()
{
SetFlyBehavior(new FlyNoWay());
SetQuackBehavior(new Squeak());
}
virtual ~RubberDuck(){}
virtual void Display() {
cout<<"I'm a rubber duckie."<<endl;
}
};
class ModelDuck:public Duck
{
public:
ModelDuck()
{
SetFlyBehavior(new FlyNoWay());
SetQuackBehavior(new RealQuack());
}
virtual ~ModelDuck(){}
virtual void Display()
{
cout<<"I'm a model duck."<<endl;
}
};
class DecoyDuck: public Duck
{
public:
DecoyDuck()
{
SetFlyBehavior(new FlyNoWay());
SetQuackBehavior(new MuteQuack());
}
virtual ~DecoyDuck(){}
virtual void Display()
{
cout<<"I'm a duck Decoy."<<endl;
}
};
void StrategyTest()
{
MallardDuck* mallard = new MallardDuck();
RubberDuck* rubberDuckie = new RubberDuck();
DecoyDuck* decoy = new DecoyDuck();
ModelDuck* model = new ModelDuck();
mallard->Display();
mallard->PerformQuack();
mallard->PerformFly();
cout<<endl;
rubberDuckie->Display();
rubberDuckie->PerformQuack();
rubberDuckie->PerformFly();
cout<<endl;
decoy->Display();
decoy->PerformQuack();
decoy->PerformFly();
cout<<endl;
model->Display();
model->PerformQuack();
model->PerformFly();
model->SetFlyBehavior(new FlyRocketPowered());
model->PerformFly();
}
void main(void)
{
StrategyTest();
system("pause");
}