思考如下场景:
有一天,刘同学准备去买笔记本,他到商城发现有两款电脑他特别喜欢, 一款是 Macbook Pro, 另一款是 Surface Pro。请同程序实现!
简单工厂模式:用于没有产品族并且产品个数较少(Spring-BeanFactory)
- 定义:专门定义一个类(第三方)用来创建其他类实例(解耦,将客户端创建对象的操作解耦到外部第三方类中),被创建的实例通常都具有共同的父类
- 组成:一个抽象产品类、N个具体产品类、一个工厂类
import java.util.Scanner;
interface Computer {
void printComputer();
}
class MacbookProComputer implements Computer {
public void printComputer() {
System.out.println("This is a MacbookPro");
}
}
class SurfaceBookComputer implements Computer {
public void printComputer() {
System.out.println("This is a SurfaceBook");
}
}
class ComputerFactory {
public static Computer getInstance(String type) {
if (type.equals("macbook")) {
return new MacbookProComputer();
}else if (type.equals("surface")) {
return new SurfaceBookComputer();
}
return null;
}
}
public class Test {
public static void main(String[] args) {
Scanner scanner = new Scanner(System.in);
System.out.println("请输入您想要的电脑型号...");
String type = scanner.nextLine();
Computer computer = ComputerFactory.getInstance(type);
computer.printComputer();
}
}
简单工厂模式优缺点
优点
- 简单易于实现
- 把类的实例化交给工厂,易于解耦。
缺点
- 添加具体产品需要修改工厂
- 违反OCP开放封闭原则
工厂方法模式(优点在于横向扩展)—产品族(Spring-FactoryBean)
- 定义一个用来创建对象的接口,让子类决定实例化哪一个工厂
- 组成:一个抽象产品类、多个具体产品类、一个抽象工厂、多个具体工厂(每个产品族对应一个具体工厂)
import java.util.Scanner;
interface Computer {
void printComputer();
}
class MacbookProComputer implements Computer {
public void printComputer() {
System.out.println("This is a MacbookPro");
}
}
class SurfaceBookComputer implements Computer {
public void printComputer() {
System.out.println("This is a SurfaceBook");
}
}
interface ComputerFactoey {
Computer creatComputer();
}
class MsFactory implements ComputerFactoey {
public Computer creatComputer() {
return new SurfaceBookComputer();
}
}
class AppleFactory implements ComputerFactoey {
public Computer creatComputer() {
return new MacbookProComputer();
}
}
public class Test {
public static void main(String[] args) {
ComputerFactoey factoey = new AppleFactory();
Computer computer = factoey.creatComputer();
computer.printComputer();
}
}
工厂方法模式优缺点
优点
- 降低了代码耦合度,对象的生成交给子类去完成 。
- 实现了开放封闭原则 – 每次添加子产品,不需要修改原有代码。
缺点
- 增加了代码量,每个具体产品都需要一个具体工厂。
- 当增加抽象产品也就是添加一个其他产品族,需要修改工厂,违背OCP。
抽象工厂—多个产品线混合
- 定义:提供一个创建一系列相关或相互依赖对象的接口(抽象工厂、多条产品线),而无需指定它们具体的类
- 工厂方法模式和抽象工厂模式基本类似,可以这么理解:当工厂只生产一个产品的时候,即为工厂方法模式,而工 厂如果生产两个或以上的商品即变为抽象工厂模式。
import java.util.Scanner;
interface Computer {
void printComputer();
}
//-----------------------------------------------------电脑产品类
class MacbookProComputer implements Computer {
public void printComputer() {
System.out.println("This is a MacbookPro");
}
}
class SurfaceBookComputer implements Computer {
public void printComputer() {
System.out.println("This is a SurfaceBook");
}
}
//-----------------------------------------------------
interface OperatingSystem {
void printSystem();
}
//-----------------------------------------------------操作系统产品类
class MacOsSystem implements OperatingSystem {
public void printSystem() {
System.out.println("This is a MacOS");
}
}
class Windows8System implements OperatingSystem {
public void printSystem() {
System.out.println("This is a Windows8");
}
}
//-----------------------------------------------------
//-----------------------------------------------------抽象工厂类
interface ProductFactoey {
Computer createComputer();
OperatingSystem createSystem();
}
//-----------------------------------------------------
class MsFactory implements ProductFactoey { //微软工厂
public Computer createComputer() { //微软电脑
return new SurfaceBookComputer();
}
public OperatingSystem createSystem() { //微软系统
return new Windows8System();
}
}
class AppleFactory implements ProductFactoey { //苹果工厂
public Computer createComputer() { //苹果电脑
return new MacbookProComputer();
}
public OperatingSystem createSystem() { //苹果系统
return new MacOsSystem();
}
}
public class Test {
public static void main(String[] args) {
ProductFactoey factory = new AppleFactory();
Computer computer = factory.createComputer();
OperatingSystem system = factory.createSystem();
computer.printComputer();
system.printSystem();
}
}
抽象工厂模式优缺点
优点
- 代码解耦
- 实现多个产品族(相关联产品组成的家族),而工厂方法模式的单个产品,可以满足更多的生产需求
- 很好的满足OCP开放封闭原则
- 抽象工厂模式中我们可以定义实现不止一个接口,一个工厂也可以生成不止一个产品类。对于复杂对象的生产相当灵活易扩展。
缺点
- 扩展产品族相当麻烦,而且扩展产品族会违反OCP,因为要修改所有的工厂。
- 由于抽象工厂模式是工厂方法模式的扩展,总体的来说,很笨重。
工厂模式总结
- 简单工厂模式最大的优点就是工厂内有具体的逻辑去判断生成什么产品,将类的实例化交给了工厂,这样当我们需要什么产品只需要修改工厂的调用而不需要去修改客户端,对于客户端来说降低了与具体产品的依赖。
- 工厂方法模式是简单工厂的扩展,工厂方法模式把原先简单工厂中的实现那个类的逻辑判断交给了客户端,如果想添加功能只需要修改客户和添加具体的功能,不用去修改之前的类。
- 抽象工厂模式进一步扩展了工厂方法模式,它把原先的工厂方法模式中只能有一个抽象产品不能添加产品族的缺点克服了,抽象工厂模式不仅仅遵循了OCP原则,而且可以添加更多产品(抽象产品),具体工厂也不仅仅可以生成单一产品,而是生成一组产品,抽象工厂也是声明一组产品,对应扩展更加灵活,但是要是扩展族系就会很笨重。
JDK中用到工厂模式的典型操作:
- Collection中的iterator方法 (集合类中的迭代器)
- java.util包中的sql相关操作