一、核心概念:一个形象的比喻
想象一下你要买家具:
-
工厂模式: 就像一个专门的工厂。
- 比如一个椅子工厂。你告诉它:“我要一把椅子。”它就会给你生产一把椅子。你不需要关心它是木椅子还是铁椅子,反正你得到的就是一把椅子。
- 再比如一个桌子工厂。你告诉它:“我要一张桌子。”它就会给你生产一张桌子。
-
抽象工厂模式: 就像一家综合性家具商城或风格套装工厂。
-
你告诉商城:“我要一套现代风格的家具。”商城就会给你配套的现代风格椅子、现代风格桌子、现代风格沙发。
-
如果你说:“我要一套维多利亚风格的家具。”商城就会给你配套的维多利亚风格椅子、维多利亚风格桌子、维多利亚风格沙发。
-
它的核心是提供一整套相关联、配套的产品。
-
二、代码示例:一看就懂
假设我们有两种产品:Button (按钮) 和 TextField (文本框)。它们有不同的风格:Light (浅色系) 和 Dark (深色系)。
- 工厂模式 (Factory Method)
工厂模式关心的是单个产品的创建。它为每一种产品提供一个工厂。
// 1. 产品接口
public interface Button {
void render();
}
public interface TextField {
void render();
}
// 2. 具体产品
public class LightButton implements Button {
@Override public void render() { System.out.println("渲染一个浅色按钮"); }
}
public class DarkButton implements Button {
@Override public void render() { System.out.println("渲染一个深色按钮"); }
}
public class LightTextField implements TextField {
@Override public void render() { System.out.println("渲染一个浅色文本框"); }
}
public class DarkTextField implements TextField {
@Override public void render() { System.out.println("渲染一个深色文本框"); }
}
// 3. 工厂接口 - 每个工厂只负责一种产品
public interface ButtonFactory {
Button createButton(); // 工厂方法
}
public interface TextFieldFactory {
TextField createTextField();
}
// 4. 具体工厂
public class LightButtonFactory implements ButtonFactory {
@Override public Button createButton() { return new LightButton(); }
}
public class DarkButtonFactory implements ButtonFactory {
@Override public Button createButton() { return new DarkButton(); }
}
// 客户端代码
public class Client {
public static void main(String[] args) {
// 创建一个深色按钮
ButtonFactory darkButtonFactory = new DarkButtonFactory();
Button button = darkButtonFactory.createButton();
button.render(); // 输出: "渲染一个深色按钮"
// 注意:要创建一个深色系界面,我需要分别创建按钮工厂和文本框工厂
// 无法保证它们来自同一风格系列
}
}
工厂模式的特点:一个工厂类只负责创建一种具体产品。
- 抽象工厂模式 (Abstract Factory)
抽象工厂模式关心的是产品族的创建。一个工厂能创建一整套有关联的产品。
// 1. 产品接口
public interface Button {
void render();
}
public interface TextField {
void render();
}
// 2. 具体产品
public class LightButton implements Button {
@Override public void render() { System.out.println("渲染一个浅色按钮"); }
}
public class DarkButton implements Button {
@Override public void render() { System.out.println("渲染一个深色按钮"); }
}
public class LightTextField implements TextField {
@Override public void render() { System.out.println("渲染一个浅色文本框"); }
}
public class DarkTextField implements TextField {
@Override public void render() { System.out.println("渲染一个深色文本框"); }
}
// 2. 抽象工厂接口 - 一个工厂能创建一整套产品!
public interface GUIFactory {
Button createButton();
TextField createTextField();
}
// 3. 具体工厂 - 每个工厂代表一个产品族
public class LightThemeFactory implements GUIFactory {
@Override public Button createButton() { return new LightButton(); }
@Override public TextField createTextField() { return new LightTextField(); }
}
public class DarkThemeFactory implements GUIFactory {
@Override public Button createButton() { return new DarkButton(); }
@Override public TextField createTextField() { return new DarkTextField(); }
}
// 客户端代码
public class Client {
public static void main(String[] args) {
// 想要一套深色风格的UI?
GUIFactory factory = new DarkThemeFactory(); // 只需选择一次风格
// 从同一个工厂创建一套配套的产品
Button button = factory.createButton();
TextField textField = factory.createTextField();
button.render(); // 输出: "渲染一个深色按钮"
textField.render(); // 输出: "渲染一个深色文本框"
// 完美保证button和textField都是Dark风格的,不会出错
}
}
抽象工厂模式的特点:一个工厂类可以创建一整套相关的产品。
三、区别与联系总结(面试直接背)
| 特性 | 工厂模式 (Factory Method) | 抽象工厂模式 (Abstract Factory) |
|---|---|---|
| 核心意图 | 封装单个对象的创建,让子类决定实例化哪个类。 | 封装一系列相关联或依赖对象的创建,而不指定它们的具体类。 |
| 关注点 | 单一产品的创建。 | 产品族的创建。确保一系列产品是兼容的、配套的。 |
| 工厂职责 | 一个工厂类只负责创建一种产品。 | 一个工厂类负责创建多个不同但相关联的产品。 |
| 扩展方式 | 要增加一种新产品(如RadioButton),需要增加一个新的工厂类。 | 要增加一个新产品族(如OceanBlueTheme),只需要增加一个新的具体工厂。 |
| 难度/复杂度 | 相对简单,易于理解和实现。 | 相对复杂,需要预先设计好产品族的抽象。 |
| 著名应用 | java.util.Calendar#getInstance(), java.text.NumberFormat#getInstance() | java.sql.Connection (它可以创建Statement, PreparedStatement等一套数据库相关对象) |
联系:
- 都是创建型模式:核心目标都是解耦客户代码和具体类的实例化过程。
- 都遵循“依赖倒置”原则:客户代码只依赖抽象接口(Product, Factory),而不依赖具体实现。
- 抽象工厂模式通常使用工厂模式来实现:在抽象工厂的具体工厂里(如DarkThemeFactory),createButton()方法本身就是一个工厂方法。
四、总结
-
工厂模式和抽象工厂模式的核心区别在于职责的粒度不同。
-
工厂模式就像一个specialists (专家),它只负责把某一种产品(比如椅子)造得非常好,但你想要一整套家具,就得去找好几个不同的专家。
-
抽象工厂模式就像一个 general contractor (总承包商),你告诉它你要什么风格(现代风还是古典风),它就能给你提供一整套风格统一、相互配套的家具(椅子、桌子、沙发),省去了你分别找多个专家并自己搭配的麻烦。
162

被折叠的 条评论
为什么被折叠?



