Strategy模式也叫策略模式是行爲模式之一,它對一系列的算法加以封裝,爲所有算法定義一個抽象的算法接口,並通過繼承該抽象算法接口對所有的算法加以封裝和實現,具體的算法選擇交由客戶端決定(策略)
簡單來說策略模式就是將算法封裝起來並能相互替換,使算法的變化獨立於客戶端之外。
具體事例:
//定義角色移動的算法的抽象類
class Move
{
public:
virtual void moveAction() = 0;
};
//移動算法的具體實現之跳躍移動
class Jump : public Move
{
public:
void moveAction()
{
cout<<"跳躍"<<endl;
}
};
//移動算法的具體實現之橫着走
class Slide : public Move
{
public:
void moveAction()
{
cout<<"橫着走"<<endl;
}
};
//移動算法的具體實現之飛行
class Fly : public Move
{
public:
void moveAction()
{
cout<<"飛行"<<endl;
}
};
//移動算法的具體實現之普通行走
class Walk : public Move
{
public:
void moveAction()
{
cout<<"行走"<<endl;
}
};
上面封裝了一系列的移動算法族,繼續添加使用算法的客戶端
class Hero
{
public:
//使用算法
virtual void action()
{
m_move->moveAction();
}
//設置使用哪種移動算法
void setMove(Move *move)
{
m_move = move;
}
private:
Move *m_move; //面對接口編程,不面向具體的行走算法
};
class Bird : public Hero{};
class People :public Hero{};
class Prab :public Hero{}; //螃蟹
class Frog :public Hero{}; //青蛙
最後我們實現這個例子
首先我們創建一個人類主角,此時的人類還是原始人,只能靠普通行走
//人是靠行走
Hero *people = new People;
people->setMove(new Walk);
people->action();
鳥兒用翅膀在天空飛
//鳥是靠翅膀飛
Hero *bird = new Bird;
bird ->setMove(new Fly);
bird->action();
人看到之後說不行我也要在天空飛
//現在人有了飛機也可以飛了
cout<<"\n"<<"人有飛機可以:";
people->setMove(new Fly);
people->action();
於是現在人也會飛了,假如現在人本事更大了,其餘的物種都怕他,那麼他進一步又可以橫着走了...
int main(int argc, char *args[])
{
//人是靠行走
Hero *people = new People;
people->setMove(new Walk);
people->action();
//鳥是靠翅膀飛
Hero *bird = new Bird;
bird ->setMove(new Fly);
bird->action();
//現在人有了飛機也可以飛了
cout<<"\n"<<"人有飛機可以:";
people->setMove(new Fly);
people->action();
delete people;
delete bird;
getchar();
return 0;
}
策略模式優缺點
它的優點有:
1. 策略模式提供了管理相關的算法族的辦法。策略類的等級結構定義了一個算法或行爲族。恰當使用繼承可以把公共的代碼移到父類裏面,從而避免重複的代碼。
2. 策略模式提供了可以替換繼承關係的辦法。繼承可以處理多種算法或行爲。如果不是用策略模式,那麼使用算法或行爲的環境類就可能會有一些子類,每一個子類提供一個不同的算法或行爲。但是,這樣一來算法或行爲的使用者就和算法或行爲本身混在一起。決定使用哪一種算法或採取哪一種行爲的邏輯就和算法或行爲的邏輯混合在一起,從而不可能再獨立演化。繼承使得動態改變算法或行爲變得不可能。
3. 使用策略模式可以避免使用多重條件轉移語句。多重轉移語句不易維護,它把採取哪一種算法或採取哪一種行爲的邏輯與算法或行爲的邏輯混合在一起,統統列在一個多重轉移語句裏面,比使用繼承的辦法還要原始和落後。
策略模式的缺點有:
1. 客戶端必須知道所有的策略類,並自行決定使用哪一個策略類。這就意味着客戶端必須理解這些算法的區別,以便適時選擇恰當的算法類。換言之,策略模式只適用於客戶端知道所有的算法或行爲的情況。
2. 策略模式造成很多的策略類。有時候可以通過把依賴於環境的狀態保存到客戶端裏面,而將策略類設計成可共享的,這樣策略類實例可以被不同客戶端使用。換言之,可以使用享元模式來減少對象的數量。