1. 概述
简单工厂模式又叫做静态工厂方法(Static Factory Method)模式,不属于23种GOF设计模式之一。
简单工厂模式是由一个工厂对象决定创建出哪一种产品类的实例。简单工厂模式是工厂模式家族中最简单实用的模式,可以理解为是不同工厂模式的一个特殊实现。
2. 示例程序
简单工厂模式要有一个工厂类,这里其名为Factory。
一个产品接口类,IProduct类。
一些实际产品,Product类,Product类需要实现产品接口类(IProduct),Product类可以有多个,例如Product01,Product02,Product03。
工厂可以通过传入的参数生成具体的产品,类图如下所示:
工厂类,Factory.java,工厂对象根据用户的请求决定创建出哪一种产品类的实例,通过一个静态方法 public static IProduct getIProductInstance(String className)创建实例,className是用户的请求。
package simpleFactory.example;
public class Factory {
public static IProduct getIProductInstance(String className) {
IProduct result = null;
if(className.equals("product01")) {
result = new Product01();
} else if(className.equals("product02")){
result = new Product02();
} else if(className.equals("product03")){
result = new Product03();
}
return result;
}
}
产品接口类,IProduct.java:
package simpleFactory.example;
public interface IProduct {
public void use();
}
具体产品类实现产品接口,Product01.java:
package simpleFactory.example;
public class Product01 implements IProduct {
@Override
public void use() {
System.out.println("use product01");
}
}
具体产品类实现产品接口,Product02.java:
package simpleFactory.example;
public class Product02 implements IProduct {
@Override
public void use() {
System.out.println("use product02");
}
}
具体产品类实现产品接口,Product03.java:
package simpleFactory.example;
public class Product03 implements IProduct {
@Override
public void use() {
System.out.println("use product03");
}
}
测试类,main.java:
package simpleFactory.example;
public class main {
public static void main(String args[]) {
IProduct iProduct = Factory.getIProductInstance("product03");
iProduct.use();
iProduct = Factory.getIProductInstance("product02");
iProduct.use();
iProduct = Factory.getIProductInstance("product01");
iProduct.use();
}
}
运行截图:
3. 具体产品很多
上述的示例有一个问题,如果具体物品很多的话,工厂类中中的分支语句(if,else)写不完了。
if(className.equals("product01")) {
result = new Product01();
} else if(className.equals("product02")){
result = new Product02();
} else if(className.equals("product03")){
result = new Product03();
}
...
使用反射可以解决上述问题,修改工厂类,通过类的绝对路径名获得其class,再获得他的实例。Factory01.java:
package simpleFactory.example1;
import simpleFactory.example.IProduct;
public class Factory01 {
public static IProduct getIProductInstance(String className) {
IProduct result = null;
try {
result = (IProduct) Class.forName(className).newInstance();
} catch (Exception e) {
e.printStackTrace();
}
return result;
}
}
测试类,main.java,simpleFactory.example.Product01为类的路径:
package simpleFactory.example1;
import simpleFactory.example.IProduct;
public class main {
public static void main(String args[]) {
IProduct iProduct = Factory01.getIProductInstance("simpleFactory.example.Product01");
iProduct.use();
iProduct = Factory01.getIProductInstance("simpleFactory.example.Product02");
iProduct.use();
iProduct = Factory01.getIProductInstance("simpleFactory.example.Product03");
iProduct.use();
}
}
运行截图如下所示:
4. 多类产品
假如有多类产品,例如添加了用户类,类图如下所示。
可以使用泛型来解决这个问题,不固定的去使用IProduct。
工厂类,Factory03.java,如下所示:
package simpleFactory.example2;
public class Factory03 {
public static <T> T getIProductInstance(String className) {
T result = null;
try {
result = (T) Class.forName(className).newInstance();
} catch (Exception e) {
e.printStackTrace();
}
return result;
}
}
测试类,main.java:
package simpleFactory.example2;
public class main {
public static void main(String args[]) {
IProduct iProduct = Factory03.getIProductInstance("simpleFactory.example2.Product01");
iProduct.use();
iProduct = Factory03.getIProductInstance("simpleFactory.example2.Product02");
iProduct.use();
iProduct = Factory03.getIProductInstance("simpleFactory.example2.Product03");
iProduct.use();
IUser iUser = Factory03.getIProductInstance("simpleFactory.example2.User03");
iUser.use();
iUser = Factory03.getIProductInstance("simpleFactory.example2.User02");
iUser.use();
iUser = Factory03.getIProductInstance("simpleFactory.example2.User01");
iUser.use();
}
}
运行截图: