下面对问题解决内容分三种:不使用工厂模式;使用简单工厂模式;使用工厂模式。
题目:
宝马(BMW)和奔驰(Benz)汽车都由汽车工厂生产,为两种品牌的汽车提供一个工厂(简单工厂)生产这两种品牌的汽车。现汽车工厂进行改革,宝马工厂专门生产宝马汽车,奔驰工厂专门生产奔驰汽车。对简单工厂模式的汽车工厂进行分割,使用工厂方法模式模拟特定的工厂生产特定品牌的汽车。要求在实现时引入配置文件,使得整个系统具有灵活性和可扩展性,方便未来增加新的工厂。
不使用工厂模式:
/**
*这个是不使用工程模式的代码
* 新建一个接口,叫Factory
* 接口内有一个方法,叫create(),等待被继承
* @author
*
*/
public interface Factory {
public void create();
}
/**
* 构建一个BMW类,继承Factory接口
* 实现create方法,输出(生产宝马汽车)
* @author
*
*/
public class BMW implements Factory {
@Override
public void create() {
// TODO Auto-generated method stub
System.out.println("生产宝马汽车");
}
}
/**
* 构建一个Benz类,继承Factory接口
* 实现create方法,输出(生产奔驰汽车)
* @author
*
*/
public class Benz implements Factory {
@Override
public void create() {
// TODO Auto-generated method stub
System.out.println("生产奔驰汽车");
}
}
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
/**
* 构造一个测试类
* @author
*
*/
public class NoFactory {
public static void main(String[] args) {
// TODO Auto-generated method stub
Factory fact = null;
String carBrand = getBrand();
if(carBrand.equalsIgnoreCase("BMW")) {
System.out.println("汽车公司正在生产汽车");
fact = new BMW();
}else if(carBrand.equalsIgnoreCase("Benz")) {
System.out.println("汽车公司正在生产汽车");
fact = new Benz();
}else {
System.out.println("当前未生产此品牌的汽车");
}
fact.create();
}
public static String getBrand() {
try {
BufferedReader strin = new BufferedReader(new InputStreamReader(System.in));
System.out.println("请输入汽车品牌");
String str = strin.readLine();
return str;
}catch(IOException e) {
e.printStackTrace();
return "";
}
}
}
使用简单工程模式:
/**
* 简单工程类(不满足开闭原则)
* @author
*
*/
public class SimpleFactory {
public static Factory produceCar(String carBrand) {
Factory fact = null;
System.out.println("使用简单工厂模式");
if(carBrand.equalsIgnoreCase("BMW")) {
System.out.println("汽车工厂生产宝马汽车");
return new BMW();
}else if(carBrand.equalsIgnoreCase("Benz")){
System.out.println("汽车工厂生产奔驰汽车");
return new Benz();
}else {
System.out.println("当前为生产此品牌的汽车");
}
return fact;
}
}
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
/**
* 测试一下简单工厂类
* @author
*
*/
public class SimpleText {
public static void main(String[] args) {
// TODO Auto-generated method stub
Factory fact = null;
String carBrand = getBrand();
try {
fact = SimpleFactory.produceCar(carBrand);
}catch(Exception e) {
e.printStackTrace();
}
fact.create();
}
public static String getBrand() {
try {
BufferedReader strin = new BufferedReader(new InputStreamReader(System.in));
System.out.println("请输入汽车的品牌:");
String str = strin.readLine();
return str;
}catch(IOException e) {
e.printStackTrace();
return "";
}
}
}
使用工厂模式:
建立一个工厂接口:
public interface CarFactory {
public Factory produceCar();
}
建立两个具体工厂:
public class BenzFactory implements CarFactory {
@Override
public Factory produceCar() {
// TODO Auto-generated method stub
System.out.println("Benz工厂生产Benz汽车。");
return new Benz();
}
}
public class BMWFactory implements CarFactory {
public Factory produceCar() {
System.out.println("BMW工厂生产BMW汽车。");
return new BMW();
}
}
客户端测试:
public class FactoryText3 {
public static void main(String[] args) {
// TODO Auto-generated method stub
System.out.println("使用工厂方法模式");
CarFactory carFactory;
Factory fact = null;
carFactory = (CarFactory)XMLUtil.getBean();
fact = carFactory.produceCar();
fact.create();
}
}
配置文件(+反射机制)实现开闭原则
<?xml version="1.0" encoding="UTF-8"?>
<config>
<className>xyq.car.factory.BMWFactory</className>
</config>
import javax.xml.parsers.*;
import org.w3c.dom.*;
import java.io.*;
public class XMLUtil {
//该方法用于从XML配置文件中提取具体类类名,并返回一个实例对象
public static Object getBean()
{
try
{
//创建文档对象
DocumentBuilderFactory dFactory = DocumentBuilderFactory.newInstance();
DocumentBuilder builder = dFactory.newDocumentBuilder();
Document doc;
doc = builder.parse(new File("src/xyq/car/factory/config.xml"));
//获取包含类名的文本节点
NodeList nl = doc.getElementsByTagName("className");
Node classNode=nl.item(0).getFirstChild();
String cName=classNode.getNodeValue();
//通过类名生成实例对象并将其返回
Class<?> c=Class.forName(cName);
Object obj=c.newInstance();
return obj;
}
catch(Exception e)
{
e.printStackTrace();
return null;
}
}
}
注:
不使用工厂模式和使用简单工厂模式两个代码都是纯Java,后期通过输入,得出结果。工厂模式需要有配置文件(+反射机制),因为我没有设置变量,所以结果无需输入,自动显示。写得很粗糙,欢迎指正,留言都会回复。