索引

别名

  • Kit

意图

提供一个创建一系列相关或相互依赖对象的接口,而无需指定它们具体的类。

Provide an interface for creating families of related or dependent objects without specifying their concrete classes.

结构

参与者

AbstractFactory

  • 声明一个创建抽象产品对象的操作接口。

ConcreteFactory

  • 实现创建具体产品对象的操作。

AbstractProduct

  • 为一类产品对象声明一个接口。

ConcreteProduct

  • 定义一个将被相应的具体工厂创建的产品对象。
  • 实现 AbstractProduct 接口。

Client

  • 仅适用由 AbstractFactory 和 AbstractProduct 类声明的接口。

适用性

在以下情况下可以使用 Abstract Factory 模式:

  • 一个系统要独立于它的产品的创建、组合和表示时。
  • 一个系统要由多个产品系列中的一个来配置时。
  • 当你要强调一系列相关的产品对象的设计以便进行联合使用时。
  • 当你提供一个产品类库,而只想显示它们的接口而不是实现时。

缺点

  • 难以支持新种类的产品。支持新种类的产品就需要扩展 AbstractFactory 接口,这将引起所有子类的改变。

效果

  • 它分离了具体的类。
  • 它使得易于交换产品系列。
  • 它有利于产品的一致性。

相关模式

命名约定

使用命名约定是一个好习惯,例如,总是声明那些定义为抽象工厂的类为 XxxKit。

实现

实现方式(一):使用 Factory Method 来实现 Abstract Factory。

一个具体的工厂将为每个产品重定义该工厂方法以指定产品。

 namespace AbstractFactoryPattern.Implementation1
{
public abstract class AbstractOrInterfaceOfFactoryKit
{
public abstract AbstractOrInterfaceOfProductA CreateProductA();
public abstract AbstractOrInterfaceOfProductB CreateProductB();
} public abstract class AbstractOrInterfaceOfProductA
{
} public abstract class AbstractOrInterfaceOfProductB
{
} public class ConcreteFactoryKit1 : AbstractOrInterfaceOfFactoryKit
{
public override AbstractOrInterfaceOfProductA CreateProductA()
{
return new ConcreteProductA();
} public override AbstractOrInterfaceOfProductB CreateProductB()
{
return new ConcreteProductB();
}
} public class ConcreteProductA : AbstractOrInterfaceOfProductA
{
} public class ConcreteProductB : AbstractOrInterfaceOfProductB
{
} public class Client
{
public void TestCase1()
{
AbstractOrInterfaceOfFactoryKit kit = new ConcreteFactoryKit1();
AbstractOrInterfaceOfProductA productA = kit.CreateProductA();
AbstractOrInterfaceOfProductB productB = kit.CreateProductB();
}
}
}

实现方式(二):使用 Prototype 来实现 Abstract Factory。

具体工厂使用产品系列中每一个产品的原型实例来初始化,且它通过复制它的原型来创建新的产品。

 namespace AbstractFactoryPattern.Implementation2
{
public abstract class AbstractOrInterfaceOfFactoryKit
{
public abstract AbstractOrInterfaceOfProductA CreateProductA();
public abstract AbstractOrInterfaceOfProductB CreateProductB();
} public abstract class AbstractOrInterfaceOfProductA
{
public abstract AbstractOrInterfaceOfProductA Clone();
} public abstract class AbstractOrInterfaceOfProductB
{
public abstract AbstractOrInterfaceOfProductB Clone();
} public class ConcreteFactoryKit1 : AbstractOrInterfaceOfFactoryKit
{
public override AbstractOrInterfaceOfProductA CreateProductA()
{
return new ConcreteProductA();
} public override AbstractOrInterfaceOfProductB CreateProductB()
{
return new ConcreteProductB();
}
} public class ConcreteFactoryKit2 : AbstractOrInterfaceOfFactoryKit
{
private AbstractOrInterfaceOfProductA _prototypeOfProductA;
private AbstractOrInterfaceOfProductB _prototypeOfProductB; public ConcreteFactoryKit2(
AbstractOrInterfaceOfProductA prototypeOfProductA,
AbstractOrInterfaceOfProductB prototypeOfProductB)
{
_prototypeOfProductA = prototypeOfProductA;
_prototypeOfProductB = prototypeOfProductB;
} public override AbstractOrInterfaceOfProductA CreateProductA()
{
return _prototypeOfProductA.Clone();
} public override AbstractOrInterfaceOfProductB CreateProductB()
{
return _prototypeOfProductB.Clone();
}
} public class ConcreteProductA : AbstractOrInterfaceOfProductA
{
public override AbstractOrInterfaceOfProductA Clone()
{
return new ConcreteProductA();
}
} public class ConcreteProductB : AbstractOrInterfaceOfProductB
{
public override AbstractOrInterfaceOfProductB Clone()
{
return new ConcreteProductB();
}
} public class Client
{
public void TestCase2()
{
AbstractOrInterfaceOfFactoryKit kit1 = new ConcreteFactoryKit1();
AbstractOrInterfaceOfProductA productA1 = kit1.CreateProductA();
AbstractOrInterfaceOfProductB productB1 = kit1.CreateProductB(); AbstractOrInterfaceOfFactoryKit kit2 = new ConcreteFactoryKit2(productA1, productB1);
AbstractOrInterfaceOfProductA productA2 = kit2.CreateProductA();
AbstractOrInterfaceOfProductB productB2 = kit2.CreateProductB();
}
}
}

实现方式(三):定义可扩展的 Abstract Factory

Abstract Factory 通常为每一种它可以生产的产品定义一个操作。产品的种类被编码在操作型构中。

增加一种新的产品要求改变 Abstract Factory 的接口以及所有与它相关的类。

一个更灵活但不太安全的设计是给创建对象的操作增加一个参数。该参数指定了将被创建的对象的种类。

该参数可以是一个类标识符、一个整数、一个字符串,或其他任何可以标识这种产品的东西。

这样改动之后,Abstract Factory 只需要一个 "Make" 操作和一个指示要创建对象的种类的参数。

 namespace AbstractFactoryPattern.Implementation3
{
public enum ProductCategory
{
ProductA,
ProductB,
} public abstract class AbstractOrInterfaceOfFactoryKit
{
public abstract object CreateProduct(ProductCategory category);
} public abstract class AbstractOrInterfaceOfProductA
{
} public abstract class AbstractOrInterfaceOfProductB
{
} public class ConcreteFactoryKit1 : AbstractOrInterfaceOfFactoryKit
{
public override object CreateProduct(ProductCategory category)
{
switch (category)
{
case ProductCategory.ProductA:
return new ConcreteProductA();
case ProductCategory.ProductB:
return new ConcreteProductB();
default:
throw new NotSupportedException();
}
}
} public class ConcreteProductA : AbstractOrInterfaceOfProductA
{
} public class ConcreteProductB : AbstractOrInterfaceOfProductB
{
} public class Client
{
public void TestCase3()
{
AbstractOrInterfaceOfFactoryKit kit = new ConcreteFactoryKit1();
AbstractOrInterfaceOfProductA productA = (AbstractOrInterfaceOfProductA)kit.CreateProduct(ProductCategory.ProductA);
AbstractOrInterfaceOfProductB productB = (AbstractOrInterfaceOfProductB)kit.CreateProduct(ProductCategory.ProductB);
}
}
}

实现方式(四):使用模板以避免创建子类。

使用C#中的泛型实现抽象工厂。

 namespace AbstractFactoryPattern.Implementation4
{
public abstract class AbstractOrInterfaceOfFactoryKit
{
public abstract AbstractOrInterfaceOfProductA CreateProductA();
public abstract AbstractOrInterfaceOfProductB CreateProductB();
public abstract AbstractOrInterfaceOfProductC CreateProductC<TC>()
where TC : AbstractOrInterfaceOfProductC, new();
} public abstract class AbstractOrInterfaceOfProductA
{
} public abstract class AbstractOrInterfaceOfProductB
{
} public abstract class AbstractOrInterfaceOfProductC
{
} public class ConcreteFactoryKit1<TA, TB> : AbstractOrInterfaceOfFactoryKit
where TA : AbstractOrInterfaceOfProductA, new()
where TB : AbstractOrInterfaceOfProductB, new()
{
public override AbstractOrInterfaceOfProductA CreateProductA()
{
return new TA();
} public override AbstractOrInterfaceOfProductB CreateProductB()
{
return new TB();
} public override AbstractOrInterfaceOfProductC CreateProductC<TC>()
{
return new TC();
}
} public class ConcreteProductA : AbstractOrInterfaceOfProductA
{
} public class ConcreteProductB : AbstractOrInterfaceOfProductB
{
} public class ConcreteProductC : AbstractOrInterfaceOfProductC
{
} public class Client
{
public void TestCase4()
{
AbstractOrInterfaceOfFactoryKit kit = new ConcreteFactoryKit1<ConcreteProductA, ConcreteProductB>();
AbstractOrInterfaceOfProductA productA = kit.CreateProductA();
AbstractOrInterfaceOfProductB productB = kit.CreateProductB();
AbstractOrInterfaceOfProductC productC = kit.CreateProductC<ConcreteProductC>();
}
}
}

设计模式之美》为 Dennis Gao 发布于博客园的系列文章,任何未经作者本人同意的人为或爬虫转载均为耍流氓。

设计模式之美:Abstract Factory(抽象工厂)的更多相关文章

  1. 设计模式02: Abstract Factory 抽象工厂(创建型模式)

    Abstract Factory 抽象工厂(创建型模式) 常见的对象创建方法:    //创建一个Road对象    Road road=new Road();    new的问题:    -实现依赖 ...

  2. 面向对象设计模式纵横谈:Abstract Factory 抽象工厂模式(笔记记录)

         今天是设计模式的第二讲,抽象工厂的设计模式,我们还是延续老办法,一步一步的.演变的来讲,先来看看一个对象创建的问题. 1.如何创建一个对象 常规的对象创建方法: 这样的创建对象没有任何问题, ...

  3. c++ 设计模式9 (Abstract Factory 抽象工厂模式)

    5.2 抽象工厂模式 动机:在软件系统中,经常面临着“一系列相互依赖的对象”的创建工作:同时,由于需求的变化,往往存在更多系列对象的创建工作. 代码示例: 实现利用数据库的业务逻辑,支持多数据库(Sq ...

  4. C#面向对象设计模式纵横谈——3.Abstract Factory 抽象工厂(创建型模式)

    动机(Motivation) 在软件系统中经常面临着“一系列相互依赖的对象”的创建工作,同时,由于需求变化,往往存在更多系列对象的创建工作.如何应对这种变化?如何绕过常规对象的创建,提供一种“封装机制 ...

  5. 设计模式(一): abstract factory抽象工厂模式 -- 创建型模式

    1.定义 为创建一组相关或相互依赖的对象提供一个接口,而且无需指定他们的具体类. 2.适用场景 1.一个系统要独立于它的产品创建.组合和表示. 2.一个系统要由多个产品系列中的一个来配置. 3.当你要 ...

  6. 一天一个设计模式——Abstract Factory抽象工厂模式

    一.模式说明 前面学习了工厂方法(Factory Method)模式.在工厂方法模式中,在工厂方法模式中,父类决定如何生成实例,但并不决定所要生成的具体类,具体的处理交由子类来处理.这里学习的抽象工厂 ...

  7. Java设计模式:Abstract Factory(抽象工厂)模式

    概念定义 抽象工厂(Abstract Factory)模式提供一个创建一系列相关或相互依赖对象的接口,而无需指定它们具体的类. 抽象工厂模式中,系统的产品有多于一个的产品族(一个产品族里定义多个产品) ...

  8. Abstract Factory 抽象工厂(创建型模式)

    1.常规的对象创建方法(以更换QQ空间主题为例) (这里的常规对象指的是由于业务需求,当前实例化的对象有可能被其他相似的对象(有着共同的特性)所取代,例如更换手机铃声:一首歌取代另一首歌(词,曲,和声 ...

  9. 对象创建型模式------Abstract Factory(抽象工厂)

    1. 意图    提供一个创建一系列相关或相互依赖对象的接口,而无需指定它们具体的类.2. 别名    Kit3. 动机        假设我们要开发一款游戏,当然为了吸引更多的人玩,游戏难度不能太大 ...

  10. Abstract factory抽象工厂--对象创建型

    意图: 提供一个创建一系列相关或者相互依赖对象的接口,而无需指定它们具体的类. 别名:Kit 补充: 抽象产品A : (产品A1 和产品 A2) 抽象产品B : ( 产品B1 和 产品B2) 一般情况 ...

随机推荐

  1. 《深入理解Nginx》阅读与实践(三):使用upstream和subrequest访问第三方服务

    本文是对陶辉<深入理解Nginx>第5章内容的梳理以及实现,代码和注释基本出自此书. 一.upstream:以向nginx服务器的请求转化为向google服务器的搜索请求为例 (一)模块框 ...

  2. json 判断字段

    1方式一 !("key" in obj) 方式二 obj.hasOwnProperty("key")  //obj为json对象. 2获取不确定键的值 for( ...

  3. 禅道Linux一键安装版

    禅道Linux一键安装版 Linux一键安装包内置了apache, php, mysql这些应用程序,只需要下载解压缩即可运行禅道.从7.3版本开始,linux一键安装包分为32位和64位两个包,大家 ...

  4. Cannot assign to 'self' outside of a method in the init family

    今天在重写父类的init方法时报错如下: error:Cannot assign to 'self' outside of a method in the init family 这种问题以前从来没有 ...

  5. 在Mac上安装IntelliJ IDEA

    这篇文章旨在介绍如何在Mac系统上安装IntelliJ IDEA,至于IntelliJ IDEA的介绍和使用方法,大家另行查阅,本篇的文章不再详细阐述. 简短解说,IntelliJ IDEA是可以用来 ...

  6. linux--分卷压缩解压缩

    1.先压缩目录为一个文件 root@ip# tar zcvf apk.tar apk/ 2.对文件进行切分,-d表示切分后的文件后缀已数字区分(如apk_2015.tar01,apk_2015.tar ...

  7. Linux命令(1)- grep

    1.grep 功能:查找文件里符合条件的字符串. 语法:grep [-abcEFGhHilLnqrsvVwxy][-A<显示列数>][-B<显示列数>][-C<显示列数& ...

  8. 关于ajax提交表单参数序列化和时间戳转换

    ajax提交form表单, 序列化表单的参数 //var a = $("#addfm").serialize(); //将表单的内容序列化成为一个字符串 var a = $(&qu ...

  9. Lua.LearningLua.5-document-for-luaL_findtable-function

    Learning Lua: 5 - Document for luaL_findtable() function 文档中没有找到luaL_findtable()函数的说明,这里尝试补充. LUALIB ...

  10. CentOS6.4完全安装FFmpeg手记

    鼓捣媒体的人对FFmpeg应该不会陌生,它不仅功能强大,结构优美,灵活.易扩展,也是很其他多媒体播放器的基础,例如VLC,Mplayer等等,还有好多商业播放器都用了ffmpeg,但这些商业软件却没有 ...