一. 工廠方法
定義了一個對象的接口,但由子類決定要實例化的類是哪一個.工廠方法讓類把實例化推遲到子類,
在簡單工廠中,原本是一個對象負責所有對象的實例化,現在將這個工廠提取到一個類中做一個實例化的方法.
二. 所有工廠模式都用來封裝對象的創建.工廠方法通過讓子類決定該創建的對象是什麽,來達到將對象創建的過程封裝的目的.
三.工廠方法UML類圖如下:
四. 接著"簡單工廠"中的事例,在為這個酒店開三家分店.示例代碼如下:
1. 菜肴的制作流程
package creationalPattern.factory.method;
/**
* 菜肴的制作流程
* @author Liyongbin
* @date 2011-02-06
*/
public abstract class Cuisine {
//帶有缺省的實現
public String purchase(){
return "原 料採購";
}
public String processing(){
return "烹調加工";
}
public String vendition(){
return "成品銷售";
}
}
2. 粵菜類
package creationalPattern.factory.method;
/**
* 粵菜類
* @author Liyongbin
* @date 2011-02-06
*/
public class ContoneseCuisine extends Cuisine{
@Override
public String processing() {
return "粵菜烹調加工";
}
@Override
public String purchase() {
return "粵菜原料採購";
}
@Override
public String vendition() {
return "粵菜成品銷售";
}
}
川菜類
package creationalPattern.factory.method;
/**
* 川菜類
* @author Liyongbin
* @date 2011-02-06
*/
public class SichuanCuisine extends Cuisine{
@Override
public String processing() {
return "川菜烹調加工";
}
@Override
public String purchase() {
return "川菜原料採購";
}
@Override
public String vendition() {
return "川菜成品銷售";
}
}
湘菜類
package creationalPattern.factory.method;
/**
* 湘菜類
* @author Liyongbin
* @date 2011-02-06
*/
public class HunanCuisine extends Cuisine{
@Override
public String processing() {
return "湘菜烹調加工";
}
@Override
public String purchase() {
return "湘菜原料採購";
}
@Override
public String vendition() {
return "湘菜成品銷售";
}
}
3.抽象類中工廠方法
package creationalPattern.factory.method;
/**
* 香格裡拉酒店[總店]
* @author Liyongbin
*
*/
public abstract class ShangriLaHotel {
/**
* 制作菜肴的方法[工廠方法]
* @param localCuisine生產的地方菜
* @return
*/
public abstract Cuisine cooking(String localCuisine);
/**
* 訂單方法
* @param localCuisine預訂的地方菜
*/
public void order(String localCuisine){
Cuisine cuisine;
//調用[工廠方法]
cuisine = cooking(localCuisine);
//生成出具有地方風味的菜肴
System.out.println(cuisine.purchase());
System.out.println(cuisine.processing());
System.out.println(cuisine.vendition());
}
}
4.廣州分店:
package creationalPattern.factory.method;
/**
* 香格裡拉酒店[廣州分店]
* @author Liyongbin
* @date 2011-02-06
*/
public class ShangriLaHotel4Guangzhou extends ShangriLaHotel{
/**
* 制作有本地[廣州]特色的地方[川,湘,粵]名菜
* @param localCuisine預訂的地方名菜
*/
@Override
public Cuisine cooking(String localCuisine) {
System.out.println("香格裡拉大酒店[廣州分店]");
Cuisine cuisine=null;
if (localCuisine.equalsIgnoreCase("Hunan")) {//湘菜
cuisine=new HunanCuisine();
} else if(localCuisine.equalsIgnoreCase("Sichuan")){//川菜
cuisine=new SichuanCuisine();
} else if(localCuisine.equalsIgnoreCase("Guangdong")){//粵菜
cuisine=new ContoneseCuisine();
}
return cuisine;
}
}
上海分店:
package creationalPattern.factory.method;
/**
* 香格裡拉酒店[上海分店]
* @author Liyongbin
* @date 2011-02-06
*/
public class ShangriLaHotel4ShangHai extends ShangriLaHotel{
/**
* 制作有本地[上海]特色的地方[川,湘,粵]名菜
* @param localCuisine預訂的地方名菜
*/
@Override
public Cuisine cooking(String localCuisine) {
System.out.println("香格裡拉大酒店[上海分店]");
Cuisine cuisine=null;
if (localCuisine.equalsIgnoreCase("Hunan")) {//湘菜
cuisine=new HunanCuisine();
} else if(localCuisine.equalsIgnoreCase("Sichuan")){//川菜
cuisine=new SichuanCuisine();
} else if(localCuisine.equalsIgnoreCase("Guangdong")){//粵菜
cuisine=new ContoneseCuisine();
}
return cuisine;
}
}
北京分店:
package creationalPattern.factory.method;
/**
* 香格裡拉酒店[北京分店]
* @author Liyongbin
* @date 2011-02-06
*/
public class ShangriLaHotel4BeiJing extends ShangriLaHotel{
/**
* 制作有本地[北京]特色的地方[川,湘,粵]名菜
* @param localCuisine預訂的地方名菜
*/
@Override
public Cuisine cooking(String localCuisine) {
System.out.println("香格裡拉大酒店[北京分店]");
Cuisine cuisine=null;
if (localCuisine.equalsIgnoreCase("Hunan")) {//湘菜
cuisine=new HunanCuisine();
} else if(localCuisine.equalsIgnoreCase("Sichuan")){//川菜
cuisine=new SichuanCuisine();
} else if(localCuisine.equalsIgnoreCase("Guangdong")){//粵菜
cuisine=new ContoneseCuisine();
}else if(localCuisine.equalsIgnoreCase("Shandong")){//魯菜
cuisine=new BeiJing4Cuisine();
}
return cuisine;
}
}
5. 分店可以有自己的制作流程
package creationalPattern.factory.method;
public class BeiJing4Cuisine extends Cuisine {
//覆蓋總店的菜肴制作過程
@Override
public String purchase() {
return "魯菜原料採購";
}
//覆蓋總店的菜肴制作過程
@Override
public String processing() {
return "魯菜烹調加工";
}
//覆蓋總店的菜肴制作過程
@Override
public String vendition() {
return "魯菜成品銷售";
}
}
6. 網上訂購[工廠方法的測試]
package creationalPattern.factory.method;
/**
* 網上訂餐測試
* @author Liyongbin
* @date 2011-02-06
*/
public class FactoryMethodTest {
public static void main(String[] args) {
//預訂香格裡拉[北京]的川菜
ShangriLaHotel4BeiJing slh4bj = new ShangriLaHotel4BeiJing();
slh4bj.order("Sichuan");//除了有總店規定的幾種菜系,
slh4bj.order("Shandong");//還有自己獨特的菜系
System.out.println("---------------------");
//預訂香格裡拉[上海]的粵菜
ShangriLaHotel4ShangHai slh4sh = new ShangriLaHotel4ShangHai();
slh4sh.order("Guangdong");
System.out.println("---------------------");
//預訂香格裡拉[廣州]的湘菜
ShangriLaHotel4Guangzhou slh4gz = new ShangriLaHotel4Guangzhou();
slh4gz.order("hunan");
}
}
7. 運行結果如下: