Gof23種設計模式+簡單工廠設計模式總結(一)
阿新 • • 發佈:2019-01-25
一、軟體設計模式的種類
1.建立型模式
如何建立物件
2.結構型模式
如何實現類和物件的組合
3.行為型模式
類和物件怎麼樣互動以及怎麼樣分配職責
二、設計模式的原則
高內聚、低耦合
1.單一職責原則
類的職責比較單一,對外只提供一種功能,引起類變化的原因應該只有一個
2.開閉原則
新增新的功能時,是通過新增程式碼實現的,而不是去修改原始碼
3.里氏替換原則
任何抽象類出現的地方都可以用他的實現類來進行替換,實際就是虛擬機制,語言級別實現面向物件的功能
4.依賴倒轉原則
依賴於抽象介面,不要依賴具體的實現類,也就是針對介面程式設計
5.介面隔離原則
不要強迫使用者的程式依賴他們不需要的介面方法,一個介面只提供一種對外的功能,不應該把所有操作都封裝到一個介面中去
6.合成複用原則
如果使用繼承,會導致父類的任何變換都可能影響到子類的行為,如果使用物件組合,就降低了這種依賴關係,對於繼承和組合,優先使用組合
7.迪米特法則
一個物件應該對其他物件儘可能少地瞭解,從而降低各個物件之間的耦合,提高系統的可維護性
三、建立型模型
1.簡單工廠設計模式
簡單工廠設計模式並不屬於Gof23中設計模式之一。
1)簡單工廠設計模式的案例程式碼:
#define _CRT_SECURE_NO_WARNINGS #include <iostream> #include <string> using namespace std; class GameRole { public: virtual void roleMove() = 0; }; //向左移動 class LeftMoveRole : public GameRole { public: virtual void roleMove() { cout << "向左移動" << endl; } }; //向右移動 class RightMoveRole : public GameRole { public: virtual void roleMove() { cout << "向右移動" << endl; } }; //向左快速移動 class LeftSpeedMoveRole : public GameRole { public: virtual void roleMove() { cout << "向左快速移動" << endl; } }; //向右快速移動 class RightSpeedMoveRole : public GameRole { public: virtual void roleMove() { cout << "向右快速移動" << endl; } }; //移動的動作工廠 class MoveFactory { public: static GameRole* CreateRoleMove(string name) { if (name.compare("left") == 0) { return new LeftMoveRole; } else if (name.compare("right") == 0) { return new RightMoveRole; } else if (name.compare("leftspeed") == 0) { return new LeftSpeedMoveRole; } else if (name.compare("rightspeed") == 0) { return new RightSpeedMoveRole; } } }; int main() { GameRole *role = NULL; role = MoveFactory::CreateRoleMove("left"); role->roleMove(); delete role; role = MoveFactory::CreateRoleMove("right"); role->roleMove(); delete role; role = MoveFactory::CreateRoleMove("leftspeed"); role->roleMove(); delete role; role = MoveFactory::CreateRoleMove("rightspeed"); role->roleMove(); delete role; system("pause"); return 0; }
2).簡單工廠設計模式的優缺點以及適用場景
優點:
物件建立和使用的分離
不需要記住類名,只需要記住引數就可以,可以減少開發者的記憶的使用
缺點:
工廠類負責的定西太多,一旦受到影響,系統會不能夠工作
增加了系統中類的個數,對開發產生一些複雜度和理解度的問題
違反了“開閉原則”,新增新產品需要修改程式碼邏輯,工廠類會變得更復雜
適用場景:
工廠類建立物件比較少的情況
客戶端只知道傳入引數,具體怎麼實現並不關心的情況
2.工廠方法設計模式
工廠方法模式 = 簡單工廠模式 + 開閉原則
1).工廠方法模式案例程式碼
#define _CRT_SECURE_NO_WARNINGS #include <iostream> #include <string> using namespace std; class GameRole { public: virtual void roleMove() = 0; }; //向左移動 class LeftMoveRole : public GameRole { public: virtual void roleMove() { cout << "向左移動" << endl; } }; //向右移動 class RightMoveRole : public GameRole { public: virtual void roleMove() { cout << "向右移動" << endl; } }; //向左快速移動 class LeftSpeedMoveRole : public GameRole { public: virtual void roleMove() { cout << "向左快速移動" << endl; } }; //向右快速移動 class RightSpeedMoveRole : public GameRole { public: virtual void roleMove() { cout << "向右快速移動" << endl; } }; class AbstractFactory { public: virtual GameRole* CreateGameRole() = 0; }; class LeftRoleFactory : public AbstractFactory { public: virtual GameRole* CreateGameRole() { return new LeftMoveRole; } }; class RightRoleFactory : public AbstractFactory { public: virtual GameRole* CreateGameRole() { return new RightMoveRole; } }; class LeftSpeedRoleFactory : public AbstractFactory { public: virtual GameRole* CreateGameRole() { return new LeftSpeedMoveRole; } }; class RightSpeedRoleFactory : public AbstractFactory { public: virtual GameRole* CreateGameRole() { return new RightSpeedMoveRole; } }; int main() { GameRole *role = NULL; AbstractFactory *factory = NULL; factory = new LeftRoleFactory; role = factory->CreateGameRole(); role->roleMove(); factory = new RightRoleFactory; role = factory->CreateGameRole(); role->roleMove(); factory = new LeftSpeedRoleFactory; role = factory->CreateGameRole(); role->roleMove(); factory = new RightSpeedRoleFactory; role = factory->CreateGameRole(); role->roleMove(); system("pause"); return 0; }
2).工廠方法模式的優缺點以及適用場景
優點:
不需要記住具體的類名和具體的引數
物件建立和使用的分離
新增新功能時,無需修改原始碼,只需要新增新的程式碼即可實現
缺點:
類的個數比較多,對開發者的理解度要求高
系統的複雜度比較高
增加了系統的抽象性和理解度
適用場景:
客戶端不需要知道它所需要的物件和類
抽象工廠類通過其子類來指定建立那個物件
2.抽象工廠模式
抽象工廠角色:它聲明瞭一組用於建立一族產品的方法,每個方法對應一種產品。
具體工廠角色:實現了在抽象工廠中宣告的建立產品的方法,生成一組具體的產品,這些產品構成了一個產品族,每一個產品都位於某個產品等級結構中。
1).抽象工廠模式案例程式碼
#define _CRT_SECURE_NO_WARNINGS
#include
#include
using namespace std;
//抽象的王者榮耀程咬金角色
class AbstractRoleCYJ
{
public:
virtual void RoleName() = 0;
};
//抽象的王者榮耀后羿角色
class AbstractRoleHY
{
public:
virtual void RoleName() = 0;
};
//抽象的王者榮耀曹操角色
class AbstractRoleCC
{
public:
virtual void RoleName() = 0;
};
//我方的程咬金
class MyCYJ : public AbstractRoleCYJ
{
public:
virtual void RoleName()
{
cout << "我方的程咬金" << endl;
}
};
//敵方的程咬金
class AnotherCYJ : public AbstractRoleCYJ
{
public:
virtual void RoleName()
{
cout << "敵方的程咬金" << endl;
}
};
//我方的后羿
class MyHY : public AbstractRoleHY
{
public:
virtual void RoleName()
{
cout << "我方的后羿" << endl;
}
};
//敵方的后羿
class AnotherHY : public AbstractRoleHY
{
public:
virtual void RoleName()
{
cout << "敵方的后羿" << endl;
}
};
//我方的曹操
class MyCC : public AbstractRoleCC
{
public:
virtual void RoleName()
{
cout << "我方的曹操" << endl;
}
};
//敵方的曹操
class AnotherCC : public AbstractRoleCC
{
public:
virtual void RoleName()
{
cout << "敵方的曹操" << endl;
}
};
//抽象工廠
class AbstractFactory
{
public:
virtual AbstractRoleCYJ* CreateCYJ() = 0;
virtual AbstractRoleHY* CreateHY() = 0;
virtual AbstractRoleCC* CreateCC() = 0;
};
//我方的工廠
class MYFactory : public AbstractFactory
{
public:
virtual AbstractRoleCYJ* CreateCYJ()
{
return new MyCYJ;
}
virtual AbstractRoleHY* CreateHY()
{
return new MyHY;
}
virtual AbstractRoleCC* CreateCC()
{
return new MyCC;
}
};
//敵方的工廠
class AnotherFactory : public AbstractFactory
{
public:
virtual AbstractRoleCYJ* CreateCYJ()
{
return new AnotherCYJ;
}
virtual AbstractRoleHY* CreateHY()
{
return new AnotherHY;
}
virtual AbstractRoleCC* CreateCC()
{
return new AnotherCC;
}
};
int main()
{
AbstractFactory *f = NULL;
AbstractRoleCYJ *cyj = NULL;
AbstractRoleHY *hy = NULL;
AbstractRoleCC *cc = NULL;
f = new MYFactory();
cyj = f->CreateCYJ();
hy = f->CreateHY();
cc = f->CreateCC();
cyj->RoleName();
hy->RoleName();
cc->RoleName();
delete cyj;
delete hy;
delete cc;
f = new AnotherFactory();
cyj = f->CreateCYJ();
hy = f->CreateHY();
cc = f->CreateCC();
cyj->RoleName();
hy->RoleName();
cc->RoleName();
delete cyj;
delete hy;
delete cc;
delete f;
system("pause");
return 0;
}
2).抽象工廠模式的優缺點以及適用場景
優點:
擁有工廠模式方法的優點
當一個產品族中的多個物件被設計成一起工作的時候,能夠保證客戶端始終只使用一個產品族中的物件
符合開閉原則
缺點:
增加新產品等級結構時,需要改原始碼,違反開閉原則
適用場景:
擁有等級結構設計的系統