定义:简单工厂模式(Simple Factory Pattern),有一个提供接口的抽象类,然后实现不同功能的子类去实现抽象类,最后一个简单工厂类来完成对不同功能子类的创建。
类型:创建型模式。
类图:
![](http://images.cnitblog.com/blog/533465/201401/03192902-2348b648836047bc90bf29c5b7b0846b.x-png)
参与角色:
1. 抽象产品,提供接口供Client调用。
1. 具体产品,根据具体产品的要求去实现接口。
1. 工厂类,根据传入参数的不同,创建不同的产品。
概述:
简单工厂模式并不是GoF的23个设计模式之中,因为简单工厂模式是工厂方法模式的一种特例。但现实中,简单工厂模式使用得非常广泛,所以在此单列出予以记录。
假设有一手机代工厂,前些年买了两条手机生产线,全部代工Nokia的手机。但是随着智能手机的崛起,Nokia手机销量的大幅下滑,使得一条Nokia手机生产线不得不停工。眼看生产线停工,老板发动人脉,终于拉到了一个新的订单,代工Samsun手机。因为手机零配件基本一致,装配流程也一样,所以Nokia的手机生产线,经过细微更改就可以生产Samsung手机了,而且先前的生产工人基本不需要培训,立即就可以进入Samsung手机生产线生产了。停工的生产线又一次启动了。
这一案例正好非常适合简单工厂模式。标准流程的手机生产线,即是抽象产品类。Nokia,Samsung即是两个具体的手机生产线产品。然后工厂就根据拿到的订单,分别代工生产不同的手机。
代码:
[![复制代码](https://box.kancloud.cn/2015-10-30_5632e1b8d3b57.gif)]( "复制代码")
~~~
1 #include <iostream>
2 #include <afxcom_.h>
3 using namespace std;
4
5 class CCellPhone
6 {
7 public:
8 virtual void ProducePhone()
9 {
10 cout<<"Produce Normal Phone."<<endl;
11 }
12 };
13
14 class CNokia : public CCellPhone
15 {
16 public:
17 virtual void ProducePhone()
18 {
19 cout<<"Produce Nokia Phone."<<endl;
20 }
21 };
22
23 class CSamsung : public CCellPhone
24 {
25 public:
26 virtual void ProducePhone()
27 {
28 cout<<"Produce Samsung Phone."<<endl;
29 }
30 };
31
32 class CPhoneFactory
33 {
34 public:
35 static CCellPhone* CreatePhone(int _nType)
36 {
37 CCellPhone* pPhone = NULL;
38
39 switch (_nType)
40 {
41 case 0: // Nokia
42 pPhone = new CNokia();
43 break;
44 case 1: // Samsung
45 pPhone = new CSamsung();
46 break;
47 default:
48 ASSERT(FALSE);
49 break;
50 }
51
52 return pPhone;
53 }
54 };
55
56 int _tmain(int argc, _TCHAR* argv[])
57 {
58 // Nokia cellphone production line
59 CCellPhone* pNokiaPhone = CPhoneFactory::CreatePhone(0);
60 pNokiaPhone->ProducePhone();
61
62 // Samsung cellphone production line
63 CCellPhone* pSamsungPhone = CPhoneFactory::CreatePhone(1);
64 pSamsungPhone->ProducePhone();
65
66 delete pNokiaPhone;
67 pNokiaPhone = NULL;
68
69 delete pSamsungPhone;
70 pSamsungPhone = NULL;
71
72 return 0;
73 }
~~~
[![复制代码](https://box.kancloud.cn/2015-10-30_5632e1b8d3b57.gif)]( "复制代码")
[![复制代码](https://box.kancloud.cn/2015-10-30_5632e1b8d3b57.gif)]( "复制代码")
~~~
1 // C#代码
2 using System;
3 using System.Collections.Generic;
4 using System.Text;
5 using System.Diagnostics;
6
7
8 namespace Phone
9 {
10 public class CellPhone
11 {
12 public virtual void ProducePhone()
13 {
14 Console.WriteLine("Produce Normal Phone.");
15 }
16 }
17
18 class Nokia : CellPhone
19 {
20 public override void ProducePhone()
21 {
22 Console.WriteLine("Produce Nokia Phone.");
23 }
24 }
25
26 class Samsung : CellPhone
27 {
28 public override void ProducePhone()
29 {
30 Console.WriteLine("Produce Samsung Phone.");
31 }
32 }
33
34 public class PhoneFactory
35 {
36 public static CellPhone CreatePhone(string _strName)
37 {
38 CellPhone phone = null;
39
40 switch (_strName)
41 {
42 case "Nokia":
43 phone = new Nokia();
44 break;
45 case "Samsung":
46 phone = new Samsung();
47 break;
48 default:
49 Debug.Assert(false);
50 break;
51 }
52
53 return phone;
54 }
55 }
56
57 class Program
58 {
59 static void Main(string[] args)
60 {
61 CellPhone phone = PhoneFactory.CreatePhone("Nokia");
62 phone.ProducePhone();
63
64 phone = PhoneFactory.CreatePhone("Samsung");
65 phone.ProducePhone();
66 }
67 }
68 }
~~~
[![复制代码](https://box.kancloud.cn/2015-10-30_5632e1b8d3b57.gif)]( "复制代码")
[![复制代码](https://box.kancloud.cn/2015-10-30_5632e1b8d3b57.gif)]( "复制代码")
~~~
1 /**
2 * CellPhone.java
3 */
4
5 /**
6 * @author feihe027@163.com
7 *
8 */
9 public class CellPhone {
10
11 public static void main(String[] args) {
12 // TODO Auto-generated method stub
13
14 // Nokia cellphone production line
15 ICellPhone nokiaPhone = PhoneFactory.createPhone("Nokia");
16 nokiaPhone.producePhone();
17
18 // Samsung cellphone production line
19 ICellPhone samsungPhone = PhoneFactory.createPhone("Samsung");
20 samsungPhone.producePhone();
21 }
22
23 }
24
25
26 public class PhoneFactory {
27
28 public static ICellPhone createPhone(String _strName) {
29 ICellPhone phone = null;
30 switch (_strName) {
31 case "Nokia":
32 phone = new NokiaPhone();
33 break;
34 case "Samsung":
35 phone = new Samsung();
36 break;
37 default:
38 break;
39 }
40
41 return phone;
42 }
43 }
44
45
46 /**
47 * IEllPhone.java
48 */
49
50 /**
51 * @author feihe027@163.com
52 *
53 */
54
55 public interface ICellPhone {
56
57 // The interface that produce cellphone
58 public void producePhone();
59
60 }
61
62
63 /**
64 * NokiaPhone.java
65 */
66
67 /**
68 * @author feihe027@163.com
69 *
70 */
71
72 public class NokiaPhone implements ICellPhone {
73
74 public void producePhone()
75 {
76 System.out.println("Produce Nokia Phone.");
77 }
78 }
79
80
81 /**
82 * Samsung.java
83 */
84
85 /**
86 * @author feihe027@163.com
87 *
88 */
89 public class Samsung implements ICellPhone{
90
91 public void producePhone() {
92 System.out.println("Produce Samsung Phone.");
93 }
94
95 }
~~~
[![复制代码](https://box.kancloud.cn/2015-10-30_5632e1b8d3b57.gif)]( "复制代码")
优缺点:
1. 优点,客户不需要了解产品的具体实现过程,只需要关注生产产品的接口即好。另外客户只需要告诉工厂需要什么类型的产品,工厂即会提供给客户指定的产品。非常简单,所以在不是非常大型的项目的编程当中,经常被用到。
1. 缺点,当工厂老板拉到新顾客LG时,引入新的生产线,但是在确定生产哪种类型的手机时,必须得修改工厂类,这违背了OCP(开闭原则)。工厂方法模式就是为了解决这个问题而产生的。
参考资料:
1. 《java与模式》
1. 《UML基础、案例与应用》
1. 《大话设计模式》
1. 一些网络博客
[源代码下载](http://files.cnblogs.com/feihe0755/CellPhone.rar)
- 前言
- 设计模式六大原则
- 1——创建型模式之简单工厂模式
- 2——创建型模式之工厂方法模式
- 3——创建型模式之抽象工厂模式
- 4——创建型模式之单例模式
- 5——创建型模式之建造者模式
- 6——创建型模式之原型模式
- 7——结构型模式之适配器模式
- 8——结构型模式之桥接模式
- 9——结构型模式之组合模式
- 10——结构型模式之装饰者模式
- 11——结构型模式之外观模式
- 12——结构型模式之享元模式
- 13——结构型模式之代理模式
- 14——行为型模式之职责链模式
- 15——行为型模式之命令模式
- 16——行为型模式之解释器模式
- 17——行为型模式之迭代器模式
- 18——行为型模式之中介者模式
- 19——行为型模式之备忘录模式
- 20——行为型模式之观察者模式
- 21——行为型模式之状态模式
- 22——行为型模式之策略模式
- 23——行为型模式之模板方法模型
- 24——行为型模式之访问者模式
- 设计模式总结