背景
最近看了一篇挺有意思的漫画https://blog.csdn.net/bjweimengshu/article/details/108459337?utm_medium=distribute.pc_feed.none-task-blog-personrec_tag-7.nonecase&depth_1-utm_source=distribute.pc_feed.none-task-blog-personrec_tag-7.nonecase&request_id=5f6000f2dfc5717f9a0d7742,看了之后还是觉得基础知识不牢固,所以还是写一篇博客,学习以及分享一下工厂模式。
工厂模式
工厂模式(Factory Pattern)是 Java 中最常用的设计模式之一。这种类型的设计模式属于创建型模式,它提供了一种创建对象的最佳方式。
在工厂模式中,我们在创建对象时不会对客户端暴露创建逻辑,并且是通过使用一个共同的接口来指向新创建的对象。
正如漫画中所说的那样,当一个类的初始化方法过于复杂的时候,如果直接写在这个类的构造函数里面,会使得代码的可读性可可扩展性大大降低,这个时候,工厂类
应运而生。
简单工厂模式
代码例子引自菜鸟教程。
public interface Shape {
void draw();
}
public class Circle implements Shape{
@Override
public void draw() {
System.out.println("This is Circle.");
}
}
public class Rectangle implements Shape{
@Override
public void draw() {
System.out.println("This is Rectangle.");
}
}
public class Square implements Shape{
@Override
public void draw() {
System.out.println("This is Square.");
}
}
分别有三个形状,创建工厂类,根据需要得到想要的形状。
public class ShapeFactory {
public Shape getShape(String shapeType) {
if (shapeType == null) {
return null;
}
if (shapeType.equalsIgnoreCase("CIRCLE")) {
return new Circle();
} else if (shapeType.equalsIgnoreCase("RECTANGLE")) {
return new Rectangle();
} else if (shapeType.equalsIgnoreCase("SQUARE")) {
return new Square();
}
return null;
}
public static void main(String[] args) {
ShapeFactory shapeFactory = new ShapeFactory();
Shape circle = shapeFactory.getShape("CIRCLE");
circle.draw();
}
}
漫画里面提出了一种开闭原则,指出了简单工厂模式的缺点。
所谓面向对象的开放-封闭原则,就是在程序中对“扩展”开放,对“修改”封闭。如果每次业务改动都要增加新的if-else,就涉及对旧有代码的修改,不但容易出错,可读性也不好。
工厂模式
为了避免上述简单工厂模式的缺点,提出了工厂模式,工厂模式是对简单工厂模式的进一步解耦。
public interface Shape {
void draw();
}
public class Circle implements Shape{
@Override
public void draw() {
System.out.println("This is Circle.");
}
}
public class Rectangle implements Shape{
@Override
public void draw() {
System.out.println("This is Rectangle.");
}
}
public class Square implements Shape{
@Override
public void draw() {
System.out.println("This is Square.");
}
}
首先创建Shape工厂接口。
public interface ShapeFactory {
Shape getShape();
}
三个形状工厂类,分别实现该接口。
例如圆的工厂类:
public class CircleFactory implements ShapeFactory {
@Override
public Shape getShape() {
return new Circle();
}
}
如何获取想要的形状?
public class test {
public static void main(String[] args) throws ClassNotFoundException, IllegalAccessException, InstantiationException {
ShapeFactory circleFactory = (ShapeFactory) Class.forName("com.zhudan.factory.factorypattern.CircleFactory").newInstance();
Shape c = circleFactory.getShape();
c.draw();
}
}
这样一来,当我想要增加一个新的形状,就只需要新增相应的工厂类即可,而无需修改原来的代码。
但是缺点也是显而易见的,这样的增加,开发难度明显增加。
抽象工厂模式
同样定义三个形状类。
public interface Shape {
void draw();
}
public class Circle implements Shape{
@Override
public void draw() {
System.out.println("This is Circle.");
}
}
public class Rectangle implements Shape{
@Override
public void draw() {
System.out.println("This is Rectangle.");
}
}
public class Square implements Shape{
@Override
public void draw() {
System.out.println("This is Square.");
}
}
同样定义颜色
public interface Color {
void fill();
}
public class Red implements Color {
@Override
public void fill() {
System.out.println("Inside Red::fill() method.");
}
}
public class Green implements Color {
@Override
public void fill() {
System.out.println("Inside Green::fill() method.");
}
}
public class Blue implements Color {
@Override
public void fill() {
System.out.println("Inside Blue::fill() method.");
}
}
创建抽象工厂AbstractFactory
,ShapeFactory
继承AbstractFactory
。
public abstract class AbstractFactory {
public abstract Color getColor(String color);
public abstract Shape getShape(String shape) ;
}
public class ShapeFactory extends AbstractFactory{
@Override
public Shape getShape(String shapeType) {
if(shapeType == null){
return null;
}
if(shapeType.equalsIgnoreCase("CIRCLE")){
return new Circle();
} else if(shapeType.equalsIgnoreCase("RECTANGLE")){
return new Rectangle();
} else if(shapeType.equalsIgnoreCase("SQUARE")){
return new Square();
}
return null;
}
@Override
public Color getColor(String color) {
return null;
}
}
public class ColorFactory extends AbstractFactory {
@Override
public Shape getShape(String shapeType){
return null;
}
@Override
public Color getColor(String color) {
if(color == null){
return null;
}
if(color.equalsIgnoreCase("RED")){
return new Red();
} else if(color.equalsIgnoreCase("GREEN")){
return new Green();
} else if(color.equalsIgnoreCase("BLUE")){
return new Blue();
}
return null;
}
}
创建工厂创造器。
public class FactoryProducer {
public static AbstractFactory getFactory(String choice){
if(choice.equalsIgnoreCase("SHAPE")){
return new ShapeFactory();
}else if(choice.equalsIgnoreCase("COLOR")){
return new ColorFactory();
}
return null;
}
}
这样就可以不用创建那么多的工厂类,只需要一个“工厂类创造器”
就搞定了。
public class test {
public static void main(String[] args) {
AbstractFactory shapeFactory = FactoryProducer.getFactory("SHAPE");
Shape shape1 = shapeFactory.getShape("CIRCLE");
shape1.draw();
AbstractFactory colorFactory = FactoryProducer.getFactory("COLOR");
Color color1 = colorFactory.getColor("RED");
}
}
这样的好处,在于我可以随意创建各种各样的工厂,不需要局限于形状的范围,也可以创建颜色等等。
引自:
https://blog.csdn.net/u012156116/article/details/80857255