设计模式(四)抽象工厂模式

在上一篇文章JAVA程序员进阶(四)工厂方法模式中主要介绍了工厂方法模式,今天继续学习抽象工厂模式。

很多程序(例如QQ)都有皮肤切换功能。假设皮肤中包括:输入框、标签、按钮三种组件,每一个新皮肤都需要定义这三个组件。按照工厂方法模式来实现该功能的话,我们需要为每一个皮肤中的每一个组件定义一个工厂类,这明显太过于麻烦,所以我们引入抽象工厂模式。

抽象工厂模式:提供一个创建一系列相关或相互依赖对象的接口,而无须指定它们具体的类。抽象工厂模式又称为Kit模式,它是一种对象创建型模式。

从上图中我们可以理解两个概念:产品等级、产品族。因为皮肤的组件属于同一产品族,所以我们可以定义一个公共的工厂去生产该皮肤中的所有组件。

首先定义所有组件类型接口:

1
2
3
4
5
6
7
package info.aviraer.design_pattern.abstract_factory.common;

public interface Button {

public void display();

}

1
2
3
4
5
6
7
package info.aviraer.design_pattern.abstract_factory.common;

public interface InputBox {

public void display();

}
1
2
3
4
5
6
7
package info.aviraer.design_pattern.abstract_factory.common;

public interface Label {

public void display();

}

然后定义一个抽象的工厂接口。

1
2
3
4
5
6
7
8
9
10
11
package info.aviraer.design_pattern.abstract_factory.common;

public interface SkinFactory {

public Button createButton();

public InputBox createInputBox();

public Label createLabel();

}

接下来就可以实现每一个皮肤的具体内容:

1
2
3
4
5
6
7
8
9
10
11
package info.aviraer.design_pattern.abstract_factory.skin1;

import info.aviraer.design_pattern.abstract_factory.common.Button;

public class Skin1Button implements Button{

public void display() {
System.out.println("Skin1 button display.");
}

}

1
2
3
4
5
6
7
8
9
10
11
package info.aviraer.design_pattern.abstract_factory.skin1;

import info.aviraer.design_pattern.abstract_factory.common.InputBox;

public class Skin1InputBox implements InputBox{

public void display() {
System.out.println("Skin1 input box display.");
}

}
1
2
3
4
5
6
7
8
9
10
11
package info.aviraer.design_pattern.abstract_factory.skin1;

import info.aviraer.design_pattern.abstract_factory.common.Label;

public class Skin1Label implements Label{

public void display() {
System.out.println("Skin1 label display.");
}

}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
package info.aviraer.design_pattern.abstract_factory.skin1;

import info.aviraer.design_pattern.abstract_factory.common.Button;
import info.aviraer.design_pattern.abstract_factory.common.InputBox;
import info.aviraer.design_pattern.abstract_factory.common.Label;
import info.aviraer.design_pattern.abstract_factory.common.SkinFactory;

public class Skin1Factory implements SkinFactory{

public Button createButton() {
return new Skin1Button();
}

public InputBox createInputBox() {
return new Skin1InputBox();
}

public Label createLabel() {
return new Skin1Label();
}

}

以上就是实现一个皮肤的代码。

通过以上代码可以发现抽象工厂模式的优势在于:

1.当一个产品族中的多个对象被设计成一起工作时,它能够保证客户端始终只使用同一个产
品族中的对象

2.增加新的产品族很方便,无须修改已有系统,符合“开闭原则”。

 

劣势在于:

1.新增产品族很方便,但是新增产品等级结构会对以往的代码进行修改。

应用场景:

1.产品等级结构稳定,且产品族会进行新增、删除的情况。