设计模式(3)-对象创建型模式-Abstract Factory模式
1.对象创建型模式
1.3 Abstract Factory模式
1.3.1 需求
在下面情况能够使用Abstract Factory模式:
• 一个系统要独立于它的产品的创建、组合和表示时(这个需求和FactoryMethod类似)。
• 一个系统要由多个产品系列中的一个来配置时(这个需求也和Factory Method类似)。
• 当你要强调一系列相关的产品对象的设计以便进行联合使用时(这个需求表明一个工厂要创建多个相关的产品对象,是比FactoryMethod多的需求)。
• 当你提供一个产品类库,而仅仅想显示它们的接口而不是实现时(这个也与FactoryMethod类似)。
依据这个适应场景能够看出,AbstractFactory模式是为创建一组(有多类)相关或依赖的对象提供创建接口,而Factory Method模式(常常直接成为工厂模式)是为一类对象提供创建接口或延迟对象的创建到子类中实现。
1.3.2功能
提供一个创建一系列相关或相互依赖对象的接口,而无需指定它们详细的类。
1.3.3 结构
•A b s t r a c t F a c t o r y ( Wi d g e t F a c t o r y )
— 声明一个创建抽象产品对象的操作接口。
•C o n c r e t e F a c t o r y ( M o t i f Wi d g e t F a c t o r y ,P M Wid g e t F a c t o r y )
— 实现创建详细产品对象的操作。
•A b s t r a c t P r o d u c t ( Wi n d o w s,S c r o l l B a r )
— 为一类产品对象声明一个接口。
•C o n c r e t e P r o d u c t ( M o t i f Wi n d o w,M o t i f S c r o l l B a r )
— 定义一个将被对应的详细工厂创建的产品对象。
— 实现Ab s t r a c t P r o d u c t接口。
•C l i e n t
— 仅使用由Ab s t r a c t F a c t o r y和Ab s t r a c t P r o d u c t类声明的接口。
1.3.4 优缺点
长处:
1. 分类了详细的类:由于一个工厂封装创建产品对象的责任和过程,客户假设使用这样的模式开发一个库,使用这个库的程序就叫做客户)将仅仅须要通过抽象接口来操作实例。这意味着客户与产品类的实现分离,并且客户不须要知道产品类的详细名称,仅仅须要知道要生成这个系列产品的工厂的名称。
2. 易于交换产品系列:在改动代码时,客户程序中仅仅须要改动要生成产品的工厂,不须要改动其它不论什么代码。
3. 有利于产品的一致性:它保证了产品簇的相关性,当一个产品族中的多个对象被设计成一起工作时,它可以保证client始终仅仅使用同一个产品族中的对象。
缺点:
难以支持新种类的产品. 这是由于A b s t r a c t F a c t or y接口确定了能够被创建的产品集合。 支持新种类的产品就须要扩展该工厂接口,这将涉及A b s t r a c t F a c t o r y类及其全部子类的改变。正所谓鱼与熊掌,不可兼得啊,你打包组合在一起,自然要承担这个缺点。
1.35 样例-C++
//Product.h
#ifndef _PRODUCT_H_
#define _PRODUCT_H_
class AbstractProductA
{
public:
virtual ~AbstractProductA();
protected:
AbstractProductA();
private:
};
class AbstractProductB
{
public:
virtual ~AbstractProductB();
protected:
AbstractProductB();
private:
};
class ProductA1 :publicAbstractProductA
{
public:
ProductA1();
~ProductA1();
protected:
private:
};
class ProductA2 :publicAbstractProductA
{
public:
ProductA2();
~ProductA2();
protected:
private:
};
class ProductB1 :publicAbstractProductB
{
public:
ProductB1();
~ProductB1();
protected:
private:
};
class ProductB2 :publicAbstractProductB
{
public:
ProductB2();
~ProductB2();
protected:
private:
};
#endif //~_PRODUCT_H_ECT_H_
//Product.cpp
#include"Product.h"
#include<iostream>
using namespace std;
AbstractProductA::AbstractProductA()
{}
AbstractProductA::~AbstractProductA()
{}
AbstractProductB::AbstractProductB()
{
}
AbstractProductB::~AbstractProductB()
{
}
ProductA1::ProductA1()
{
cout << "ProductA1..."<< endl;
}
ProductA1::~ProductA1()
{
}
ProductA2::ProductA2()
{
cout << "ProductA2..."<< endl;
}
ProductA2::~ProductA2()
{
}
ProductB1::ProductB1()
{
cout << "ProductB1..."<< endl;
}
ProductB1::~ProductB1()
{
}
ProductB2::ProductB2()
{
cout << "ProductB2..."<< endl;
}
ProductB2::~ProductB2()
{
}
//AbstractFactory.h
#ifndef _ABSTRACTFACTORY_H_
#define _ABSTRACTFACTORY_H_
class AbstractProductA;
class AbstractProductB;
class AbstractFactory
{
public:
virtual ~AbstractFactory();
virtual
AbstractProductA*
CreateProductA() = 0;
virtual
AbstractProductB*
CreateProductB() = 0;
protected:
AbstractFactory();
private:
};
class ConcreteFactory1 :publicAbstractFactory
{
public:
ConcreteFactory1();
~ConcreteFactory1();
AbstractProductA* CreateProductA();
AbstractProductB* CreateProductB();
protected:
private:
};
class ConcreteFactory2 :publicAbstractFactory
{
public:
ConcreteFactory2();
~ConcreteFactory2();
AbstractProductA* CreateProductA();
AbstractProductB* CreateProductB();
protected:
private:
};
#endif //~_ABSTRACTFACTORY_H_
//AbstractFactory.cpp
#include"AbstractFactory.h"
#include"Product.h"
#include<iostream>
using namespace std;
AbstractFactory::AbstractFactory()
{
}
AbstractFactory::~AbstractFactory()
{
}
ConcreteFactory1::ConcreteFactory1()
{
}
ConcreteFactory1::~ConcreteFactory1()
{
}
AbstractProductA*
ConcreteFactory1::CreateProductA()
{
return newProductA1();
}
AbstractProductB*
ConcreteFactory1::CreateProductB()
{
return newProductB1();
}
ConcreteFactory2::ConcreteFactory2()
{
}
ConcreteFactory2::~ConcreteFactory2()
{
}
AbstractProductA*
ConcreteFactory2::CreateProductA()
{
return newProductA2();
}
AbstractProductB*
ConcreteFactory2::CreateProductB()
{
return newProductB2();
}
//main.cpp
#include"AbstractFactory.h"
#include<iostream>
using namespace std;
int main(int
argc, char*argv[])
{
AbstractFactory* cf1 =
new
ConcreteFactory1();
cf1->CreateProductA();
cf1->CreateProductB();
AbstractFactory* cf2 =
new
ConcreteFactory2();
cf2->CreateProductA();
cf2->CreateProductB();
return 0;
}
1.3.5 样例-JAVA
1. //抽象产品
2. UpperClothes.java
3. public abstract class UpperClothes {
4. public abstract int getChestSize();
5. public abstract int getHeight();
6. public abstract String getName();
7. }
8. Trousers.java
9. public abstract class Trousers {
10. public abstract int getWaistSize();
11. public abstract int getHeight();
12. public abstract String getName();
13.}
14.//详细产品
15.WesternUpperClothes.java
16.public class WesternUpperClothes extends UpperClothes {
17. private int chestSize;
18. private int height;
19. private String name;
20. WesternUpperClothes(String name,int chestSize,int height){
21. this.name=name;
22. this.chestSize=chestSize;
23. this.height=height;
24. }
25. public int getChestSize() {
26. return chestSize;
27. }
28. public int getHeight() {
29. return height;
30. }
31. public String getName() {
32. return name;
33. }
34.}
35.CowboyUpperClothes.java
36.public class CowboyUpperClothes extends UpperClothes {
37. private int chestSize;
38. private int height;
39. private String name;
40. CowboyUpperClothes(String name,int chestSize,int height){
41. this.name=name;
42. this.chestSize=chestSize;
43. this.height=height;
44. }
45. public int getChestSize() {
46. return chestSize;
47. }
48. public int getHeight() {
49. return height;
50. }
51. public String getName () {
52. return name;
53. }
54.}
55.WesternTrousers.java
56.public class WesternTrousers extends Trousers {
57. private int waistSize;
58. private int height;
59. private String name;
60. WesternTrousers(String name,int waistSize,int height){
61. this.name=name;
62. this.waistSize=waistSize;
63. this.height=height;
64. }
65. public int getHeight() {
66. return height;
67. }
68. public String getName() {
69. return name;
70. }
71. public int getWaistSize() {
72. return waistSize;
73. }
74.}
75.CowboyTrousers.java
76.public class CowboyTrousers extends Trousers {
77. private int waistSize;
78. private int height;
79. private String name;
80. CowboyTrousers(String name,int waistSize,int height){
81. this.name=name;
82. this.waistSize=waistSize;
83. this.height=height;
84. }
85. public int getHeight() {
86. return height;
87. }
88. public String getName() {
89. return name;
90. }
91. public int getWaistSize() {
92. return waistSize;
93. }
94.}
95.//抽象工厂
96.ClothesFactory.java
97.public abstract class ClothesFactory {
98. public abstract UpperClothes createUpperClothes(int chestSize,int height);
99. public abstract Trousers createTrousers(int waistSize,int height);
100. }
101. //详细工厂
102. BeijingClothesFactory.java
103. public class BeijingClothesFactory extends ClothesFactory {
104. public Trousers createTrousers(int waistSize, int height) {
105. return new WesternTrousers("北京牌裤子",waistSize,height);
106. }
107. public UpperClothes createUpperClothes(int chestSize, int height) {
108. return new WesternUpperClothes("北京牌上衣",chestSize,height);
109. }
110. }
111. ShanghaiClothesFactory.java
112. public class ShanghaiClothesFactory extends ClothesFactory {
113. public Trousers createTrousers(int waistSize, int height) {
114. return new WesternTrousers("上海牌裤子",waistSize,height);
115. }
116. public UpperClothes createUpperClothes(int chestSize, int height) {
117. return new WesternUpperClothes("上海牌上衣",chestSize,height);
118. }
119. }
package DesignPattern;
public
class TestMain {
/**
* @param args
*/
public
static void main(String[] args){
ClothesFactoryf=newShanghaiClothesFactory();
//ClothesFactoryf=new BeijingClothesFactory();
Trouserst = f.createTrousers(13, 14);
System.out.println(t.getName());
UpperClothesuc=f.createUpperClothes(13,14);
System.out.println(uc.getName());
}
}
设计模式(3)-对象创建型模式-Abstract Factory模式的更多相关文章
- 【创建型】Abstract Factory模式 & Factory Method模式
本文主要介绍简单工厂模式与抽象工厂模式.以下如有叙述不当之处,欢迎批评指正,欢迎交流探讨. 一:简单工厂模式 在23种设计模式中,简单工厂模式其实是不在列的,但理解该模式对于抽象工厂模式的思想理解是有 ...
- 设计模式(4)-对象创建型模式-Prototype模式
1.对象创建型模式 1.4 Protoype模式 1.4.1需求 通过拷贝原形对象创建新的对象. 1.4.2结构 •P r o t o t y p e(Gr a p h i c) - ...
- JAVA设计模式 3【创建型】理解工厂模式与抽象工厂模式
上一节我们已经学习了原型模式,稍微复习一下:通过重写Object 类的clone() 方法实现浅克隆,浅克隆也要实现Cloneable 标记接口.而深克隆则是将对象通过序列化和反序列化 的方式进行创建 ...
- JAVA设计模式 4【创建型】理解建造者模式
Hello,又是拖了几天更,实在是忙的要死,有时候忙累了,真的就是倒头睡的那种,刚好今天闲下来了.今天来更新一篇建造者模式. 其实建造者模式,我们已经在上一节已经有了解过了.只不过是上一节没有提到这样 ...
- 设计模式可复用面向对象软件设计基础之对象创建型模式—ABSTRACT FACTORY( 抽象工厂)
意图 提供一个创建一系列相关或相互依赖对象的接口,而无需指定它们具体的类. 适用性 在以下情况可以使用 Abstract Factory模式 • 一个系统要独立于它的产品的创建.组合和表示时. • 一 ...
- C++设计模式 之 “对象创建”模式:Factory Method、Abstract Factory、Prototype、Builder
part 0 “对象创建”模式 通过“对象创建” 模式绕开new,来避免对象创建(new)过程中所导致的紧耦合(依赖具体类),从而支持对象创建的稳定.它是接口抽象之后的第一步工作. 典型模式 Fact ...
- 对象创建型模式------Abstract Factory(抽象工厂)
1. 意图 提供一个创建一系列相关或相互依赖对象的接口,而无需指定它们具体的类.2. 别名 Kit3. 动机 假设我们要开发一款游戏,当然为了吸引更多的人玩,游戏难度不能太大 ...
- 【设计模式】抽象工厂模式 Abstract Factory Pattern
简单工厂模式是一个工厂类根据工厂方法的参数创建不出不同的产品, 工厂方法模式是每一个产品都有一个一一对应的工厂负责创建该产品.那么今天要讲的抽象工厂模式是一个工厂能够产生关联的一系列产品.抽象工厂模式 ...
- 乐在其中设计模式(C#) - 抽象工厂模式(Abstract Factory Pattern)
原文:乐在其中设计模式(C#) - 抽象工厂模式(Abstract Factory Pattern) [索引页][源码下载] 乐在其中设计模式(C#) - 抽象工厂模式(Abstract Factor ...
随机推荐
- (转)javascript中return的作用
这里面的return含有一些细节知识: 例如:onClick='return add_onclick()'与 onClick='add_onclick()'的区别 JAVASCRIPT在事件中调用函数 ...
- ORACLE输出详细错误信息错误行数
... COMMIT; --输出成功信息 DBMS_OUTPUT.PUT_LINE('RUN RESULT: SUCCESS'); EXCEPTION WHEN OTHERS THEN BEGIN R ...
- Oracle数据库锁表的查询方法以及解锁的方法
1,锁表语句简单查询方法 select t2.username,t2.sid,t2.serial#,t2.logon_time from v$locked_object t1,v$session ...
- 武汉科技大学ACM:1004: 华科版C语言程序设计教程(第二版)习题5.6
Problem Description 这天老师又给小豪出了一道题目:给你三根长度分别为a,b,c的火柴,让你计算这三跟火柴能组成的三角形的面积. Input 输入每行包括三个数a,b,c. Outp ...
- pragram once
#pragma once [1]#pragma once这个宏有什么作用? 为了避免同一个文件被include多次,C/C++中有两种宏实现方式:一种是#ifndef方式,一种是#pragma o ...
- linux入门。删除不用到内核,为boot分区释放空间
在终端中输入如下命令: dpkg --get-selections|grep linux-image 这时会列出系统中所有到内核. 你可以使用 uname -a 查看你当前使用到内核. 然后用 sud ...
- mongodb安装服务
一.准备工作 1:下载: http://www.mongodb.org/downloads 2:解压到ZIP到 D:\Mongodb ,在此目录下再建立2个目录 D:\Mongodb\db和D ...
- Nuc900 bsp turbowriter使用注意点
Nuc900 bsp turbowriter使用注意点 一. Nor flash 用turbo 烧写kernel和文件系统时的注意点: 1. kernel的image No要大于rootfs 2.烧写 ...
- javascript中的screen对象
screen对象通常包含下列属性(许多浏览器都加入了自己的属性): 1.availHeight : 窗口可以使用的屏幕的高度(以像素计)其中包括操作系统元素(如window工具栏)需要的空间. 2. ...
- centos 开启apache rewrite模式
mod_rewrite能使网页伪静态,对于搜索引擎友好,下面就是开启这个功能的说明!启用mod_rewrite模块在conf目录的httpd.conf文件中找到 LoadModule rewrite_ ...