设计模式 - 工厂模式
·
什么是工厂模式?
工厂模式是一种创建对象的设计模式,它把对象的创建过程封装起来,客户端只需要告诉工厂"我要什么",工厂就会返回相应的对象。
就像餐厅点餐:
- 你告诉服务员"我要一份宫保鸡丁"
- 厨师在后厨制作(你不需要知道怎么做)
- 服务员把做好的菜端给你
主要解决什么问题?
工厂模式主要解决以下问题:
- 对象创建复杂:对象的创建需要复杂逻辑(如读取配置、依赖组装)
- 解耦客户端:客户端代码不依赖具体类,只依赖抽象接口
- 集中管理:统一管理对象的创建和生命周期
- 避免重复代码:将创建逻辑集中在一处,避免到处写
new
何时使用工厂模式?
当你遇到以下场景时,考虑使用工厂模式:
- 需要根据不同条件创建不同对象(如不同支付方式)
- 对象的创建过程复杂(需要初始化、设置参数等)
- 希望隐藏创建细节(客户端不关心对象怎么来的)
- 需要统一管理对象的创建(如连接池、线程池)
工厂模式的优点
- 解耦:客户端和具体实现类解耦
- 可扩展:新增产品只需添加新类,符合开闭原则
- 复用:创建逻辑可以复用
- 统一管理:对象的创建和配置集中管理
- 测试友好:可以轻松替换mock对象
工厂模式的缺点
- 增加类数量:每增加一个产品可能需要增加一个工厂类
- 复杂度提升:引入抽象层次,增加理解难度
- 过度设计:简单场景用工厂反而复杂
代码示例:三种工厂模式
1. 简单工厂模式(静态工厂)
// 产品接口
interface Animal {
void speak();
}
// 具体产品:狗
class Dog implements Animal {
@Override
public void speak() {
System.out.println("汪汪汪!");
}
}
// 具体产品:猫
class Cat implements Animal {
@Override
public void speak() {
System.out.println("喵喵喵!");
}
}
// 具体产品:鸭子
class Duck implements Animal {
@Override
public void speak() {
System.out.println("嘎嘎嘎!");
}
}
// 简单工厂
class AnimalFactory {
public static Animal createAnimal(String type) {
switch (type.toLowerCase()) {
case "dog":
return new Dog();
case "cat":
return new Cat();
case "duck":
return new Duck();
default:
throw new IllegalArgumentException("未知的动物类型: " + type);
}
}
}
// 客户端使用
public class SimpleFactoryDemo {
public static void main(String[] args) {
Animal dog = AnimalFactory.createAnimal("dog");
Animal cat = AnimalFactory.createAnimal("cat");
dog.speak(); // 汪汪汪!
cat.speak(); // 喵喵喵!
}
}
特点:一个工厂生产所有产品,简单直接,但扩展性差。
2. 工厂方法模式
// 抽象工厂接口
interface AnimalFactory {
Animal createAnimal();
}
// 具体工厂:生产狗的工厂
class DogFactory implements AnimalFactory {
@Override
public Animal createAnimal() {
// 可以在这里进行复杂的初始化
System.out.println("正在初始化狗对象...");
return new Dog();
}
}
// 具体工厂:生产猫的工厂
class CatFactory implements AnimalFactory {
@Override
public Animal createAnimal() {
System.out.println("正在初始化猫对象...");
return new Cat();
}
}
// 具体工厂:生产鸭子的工厂
class DuckFactory implements AnimalFactory {
@Override
public Animal createAnimal() {
System.out.println("正在初始化鸭子对象...");
return new Duck();
}
}
// 客户端使用
public class FactoryMethodDemo {
public static void main(String[] args) {
// 每个产品对应一个工厂
AnimalFactory dogFactory = new DogFactory();
AnimalFactory catFactory = new CatFactory();
Animal dog = dogFactory.createAnimal();
Animal cat = catFactory.createAnimal();
dog.speak();
cat.speak();
}
}
特点:每个产品有自己的工厂,符合开闭原则,扩展性好。
3. 抽象工厂模式(产品族)
// 抽象产品1:食物
interface Food {
void eat();
}
// 抽象产品2:玩具
interface Toy {
void play();
}
// 具体产品:狗粮
class DogFood implements Food {
@Override
public void eat() {
System.out.println("吃狗粮");
}
}
// 具体产品:猫粮
class CatFood implements Food {
@Override
public void eat() {
System.out.println("吃猫粮");
}
}
// 具体产品:狗玩具
class DogToy implements Toy {
@Override
public void play() {
System.out.println("玩飞盘");
}
}
// 具体产品:猫玩具
class CatToy implements Toy {
@Override
public void play() {
System.out.println("玩毛线球");
}
}
// 抽象工厂:生产一组相关产品
interface PetFactory {
Animal createAnimal();
Food createFood();
Toy createToy();
}
// 具体工厂:生产狗相关的所有产品
class DogPetFactory implements PetFactory {
@Override
public Animal createAnimal() {
return new Dog();
}
@Override
public Food createFood() {
return new DogFood();
}
@Override
public Toy createToy() {
return new DogToy();
}
}
// 具体工厂:生产猫相关的所有产品
class CatPetFactory implements PetFactory {
@Override
public Animal createAnimal() {
return new Cat();
}
@Override
public Food createFood() {
return new CatFood();
}
@Override
public Toy createToy() {
return new CatToy();
}
}
// 客户端使用
public class AbstractFactoryDemo {
public static void main(String[] args) {
// 选择养狗
PetFactory dogFactory = new DogPetFactory();
Animal dog = dogFactory.createAnimal();
Food dogFood = dogFactory.createFood();
Toy dogToy = dogFactory.createToy();
dog.speak(); // 汪汪汪!
dogFood.eat(); // 吃狗粮
dogToy.play(); // 玩飞盘
System.out.println("---");
// 选择养猫
PetFactory catFactory = new CatPetFactory();
Animal cat = catFactory.createAnimal();
Food catFood = catFactory.createFood();
Toy catToy = catFactory.createToy();
cat.speak(); // 喵喵喵!
catFood.eat(); // 吃猫粮
catToy.play(); // 玩毛线球
}
}
特点:生产一系列相关的产品(产品族),保证产品之间的兼容性。
实际应用场景
工厂模式在Java中的经典应用:
-
Spring IoC容器:BeanFactory根据配置创建对象
BeanFactory factory = new ClassPathXmlApplicationContext("beans.xml"); UserService userService = factory.getBean(UserService.class); -
日志框架:LoggerFactory创建Logger
Logger logger = LoggerFactory.getLogger(MyClass.class); -
JDBC:DriverManager创建Connection
Connection conn = DriverManager.getConnection(url, username, password); -
线程池:Executors创建线程池
ExecutorService executor = Executors.newFixedThreadPool(10);
三种工厂模式的对比
| 模式 | 特点 | 适用场景 | 开闭原则 |
|---|---|---|---|
| 简单工厂 | 一个工厂生产所有产品 | 产品种类少且固定 | ❌ 违反 |
| 工厂方法 | 每个产品有自己的工厂 | 产品可能扩展 | ✅ 符合 |
| 抽象工厂 | 生产产品族(多个相关产品) | 需要配套产品 | ✅ 符合 |
选择建议
- 产品种类少且稳定 → 简单工厂
- 产品种类可能扩展 → 工厂方法
- 需要配套产品 → 抽象工厂
- 对象创建简单 → 直接
new就好,别过度设计
总结
工厂模式的核心思想是:将对象的创建和使用分离。它就像现实生活中的工厂一样,你只需要告诉工厂你要什么,工厂负责生产,你只管使用。
更多推荐
所有评论(0)