Java设计模式系列-抽象工厂模式
原创文章,转载请标注出处:Java设计模式之《抽象工厂模式》及使用场景
一、概述
抽象工厂模式是对工厂方法模式的再升级,但是二者面对的场景稍显差别。
工厂方法模式面对的目标一般都是单类的,就比如《ava设计模式之《工厂方法模式》及使用场景》中所举的例子,目标就是桌子这一类商品。
如果是这样的呢:生产的是桌椅组合,目标的一套商品,每一套商品中的每类商品的种类的不同的,不同的组合形成不同的套装。
这种情况下,就需要使用抽象工厂模式
二、实例
我们还以家具为例:
桌子接口:Desk
/**
* 桌子接口
*/
public interface Desk {
String getType();
}
木质桌子:WoodenDesk
/**
* 木质桌子
*/
public class WoodenDesk implements Desk {
private String type = "木质桌";
@Override
public String getType() {
return type;
}
}
塑料桌子:PlasticDesk
/**
* 塑料桌
*/
public class PlasticDesk implements Desk {
private String type = "塑料桌";
@Override
public String getType() {
return type;
}
}
椅子接口:Chair
/**
* 椅子接口
*/
public interface Chair {
String getType();
}
木质椅子:WoodenChair
/**
* 木质椅
*/
public class WoodenChair implements Chair {
private String type = "木质椅";
@Override
public String getType() {
return type;
}
}
塑料椅:PlasticChair
/**
* 塑料椅
*/
public class PlasticChair implements Chair {
private String type = "塑料椅";
@Override
public String getType() {
return type;
}
}
家具工厂接口:FurnitureFactory
/**
* 家具工厂
*/
public interface FurnitureFactory {
Desk createDesk();
Chair createChair();
}
木质家具工厂:WoodenFurnitureFactory
/**
* 木质家具工厂
*/
public class WoodenFurnitureFactory implements FurnitureFactory {
@Override
public Desk createDesk() {
return new WoodenDesk();
}
@Override
public Chair createChair() {
return new WoodenChair();
}
}
塑料家具工厂:PlasticFurnitureFactory
/**
* 塑料家具工厂
*/
public class PlasticFurnitureFactory implements FurnitureFactory {
@Override
public Desk createDesk() {
return new PlasticDesk();
}
@Override
public Chair createChair() {
return new PlasticChair();
}
}
测试类:Clienter
/**
* 测试类
*/
public class Clienter {
public static void main(String[] args) {
FurnitureFactory factory = new PlasticFurnitureFactory();
Desk desk = factory.createDesk();
Chair chair = factory.createChair();
System.out.println(desk.getType());
System.out.println(chair.getType());
}
}
执行结果:
塑料桌
塑料椅
三、解析
通过上面的例子,对比Java设计模式之《工厂方法模式》及使用场景中工厂方法模式的例子,可以看出二者场景的不同之处,抽象工厂模式面对的是一个组合体,如果将这一点排除的话,其他方面看起来,二者还是相似的。
这里在目标每添加一种组合时,就需要新建一个工厂实现来对应,这一点满足开闭原则,不会修改已有类。
但是有一种情况,会导致修改原有类,那就是当目标需要在家具中新增一种家具类型的时候,比如例子中,家具组合中只包含桌子和椅子,如果再添加一种书柜,那么所有的工厂包括工厂接口都面临修改。
同系列文章:
- Java设计模式之《适配器模式》及应用场景
- Java设计模式之《外观模式》及应用场景
- Java设计模式之《桥接模式》及应用场景
- Java设计模式之《单例模式》及应用场景
- Java设计模式之《观察者模式》及应用场景
- Java设计模式之《调停者模式》及应用场景
- Java设计模式之《代理模式》及应用场景
- Java设计模式之《职责链模式》及应用场景
- Java设计模式之《享元模式》及应用场景
- Java设计模式之《构建者模式》及应用场景
- Java设计模式之《模板模式》及使用场景
- Java设计模式之《装饰器模式》及应用场景
- Java设计模式之《工厂方法模式》及使用场景
- Java设计模式之《抽象工厂模式》及使用场景
Java设计模式系列-抽象工厂模式的更多相关文章
- Java 设计模式之抽象工厂模式(三)
原文地址:Java 设计模式之抽象工厂模式(三) 博客地址:http://www.extlight.com 一.前言 上篇文章 <Java 设计模式之工厂模式(二)>,介绍了简单工厂模式和 ...
- Java设计模式系列之工厂模式
工厂模式将大量有共同接口的类实例化,工厂模式可以实现动态决定实例化哪一个类的对象,工厂模式在<Java与模式>中分为三类:1)简单工厂模式(Simple Factory):添加某一种类型的 ...
- java设计模式之抽象工厂模式
上一篇文章(http://www.cnblogs.com/liaoweipeng/p/5768197.html)讲了简单工厂模式,但是简单工厂模式存在一定的问题,如果想要拓展程序,必须对工厂类进行修改 ...
- Java 设计模式之抽象工厂模式
抽象工厂模式(Abstract Factory Pattern)是围绕一个超级工厂创建其他工厂.该超级工厂又称为其他工厂的工厂.这种类型的设计模式属于创建型模式,它提供了一种创建对象的最佳方式. 在抽 ...
- java设计模式(三)--抽象工厂模式
转载:http://zz563143188.iteye.com/blog/1847029 前面的工厂方法模式虽然清晰,但还是感觉有些繁琐,通常使用的还是抽象工厂模式. 工厂方法模式有一个问题就是,类的 ...
- [java] java 设计模式(2):抽象工厂模式(Abstract Factory)
工厂方法模式有一个问题就是,类的创建依赖工厂类,也就是说,如果想要拓展程序,必须对工厂类进行修改,这违背了闭包原则,所以,从设计角度考虑,有一定的问题,如何解决?就用到抽象工厂模式,创建多个工厂类,这 ...
- Java设计模式(3)——抽象工厂模式
抽象工厂模式是所有形态的工厂模式中最为抽象和最其一般性的.抽象工厂模式可以向客户端提供一个接口,使得客户端在不必指定产品的具体类型的情况下,能够创建多个产品族的产品对象. 一.产品族和产品等级结构 为 ...
- java设计模式之抽象工厂模式学习
工厂模式有个问题就是,类的创建依赖工厂.要想增加一个工厂类,就要修改原来的代码,这违背了闭包原则.所以,从设计角度考虑,有一定的问题,如何解决?就用到抽象工厂模式,创建多个工厂类,这样一旦需要增加新的 ...
- Java设计模式之【工厂模式】(简单工厂模式,工厂方法模式,抽象工厂模式)
Java设计模式之[工厂模式](简单工厂模式,工厂方法模式,抽象工厂模式) 工厂模式出现的原因 在java中,创建一个对象最简单的方法就是使用new关键字.但在一些复杂的业务逻辑中,创建一个对象不只需 ...
随机推荐
- 深入讨论channel timeout
深入讨论channel timeout Go 语言的 channel 本身是不支持 timeout 的,所以一般实现 channel 的读写超时都采用 select,如下: select { case ...
- 认识容器和Docker(一)
前言: 这句话应该是开发人员经常挂在嘴边的吧! “在我的机器上是正常工作的啊,MD,怎么到你这就不行了?” 开发人员就会联想到: 1. 肯定是你环境有问题: 2. 要么就是你个傻*不会用吧: 带着这句 ...
- c#位运算基本概念与计算过程
前言 一些非常基础的东西,在实际工作中没有用到.很少用到.一旦遇到,又不知所云.最近遇到一个问题,把一个int16(short) .两个bool变量整合成一个int32(int),当听到这个要求时,我 ...
- Mysql存储过程历史表备份
应用背景 SCADA采集系统需要将实时数据存入历史表.问题1:如何更简单的添加历史数据?2.海量历史数据,比如年数据,如何快速筛选 画曲线? 利用mysql的事件,每小时存一次采集数据: 每月备份历史 ...
- SpringBoot之旅第五篇-数据访问
一.引言 大部分系统都离不开数据访问,数据库包括SQL和NOSQL,SQL是指关系型数据库,常见的有SQL Server,Oracle,MySQL(开源),NOSQL是泛指非关系型数据库,常见的有Mo ...
- 强化学习(十四) Actor-Critic
在强化学习(十三) 策略梯度(Policy Gradient)中,我们讲到了基于策略(Policy Based)的强化学习方法的基本思路,并讨论了蒙特卡罗策略梯度reinforce算法.但是由于该算法 ...
- JS,JQ 格式化小数位数
在<script>中: $(function(){ var num=$(".price").length;/*获取应用了class="price"的 ...
- 【Android】OkHttp3总结与封装
开始使用 在app目录下的build.gradle中添加依赖: implementation 'com.squareup.okhttp3:okhttp:3.13.1' implementation ' ...
- Maven 基本的认识
Maven 基本的认识 1. 什么是Maven? 在平时开发中,经常遇到某个jar包,我在代码层已经Import 和@Automation了,编译器还是提醒你某个jar包找不到,往往这时来个mvn i ...
- windows系统中,在当前目录下打开cmd命令行的两种方法
1.在当前路径地址栏中直接输入‘cmd’,然后回车. 2.在当前路径下,按住‘shift’键同时点击鼠标右键,点击“在此处打开Powershell”. 其实你会发现,两个命令行有很大的区别. cmd: ...