/**
* 總結:
* 策略模式和簡單工廠模式是很相似的,對於抽象父類和具體子類那里和簡單工廠是一回事
* 不過下面還多添加了一個Context類,用來調用算法接口
* 來說說簡單工廠和策略模式的區別:
* 簡單工廠是生產對象來調用對象的方法,在主函數中用簡單工廠生產對象調用方法
* 而策略模式是在Context類中生產對象,然后在Context類中調用Context中的對象的方法,在主函數中創建Context類的對象調用方法
*
*
* 總而言之 策略模式是一種定義了一系列算法的方法,(多態真是絕絕子,yyds,正是多態才完美的實現了繼承的功能 真正做到了降低代碼的冗余)
* 從context類來看我們只是創建了一個抽象父類,調用了這個抽象父類中的抽象方法,而switch去實例化它的子類,編譯是看的是父類
* 運行時,真正調用的其實是子類的方法,這就是多態。
* 如果我們想多添加功能只需要添加對應的子類,重寫方法,然后再context類中多添加一個case分支,就可以了,不需要對我們的代碼進行“大手術”
*
*/
下面先給出策略模式的模板
/**
*
* 策略模式模板
*
* 通過一個抽象父類,定義算法接口 接下來的三個子類 StrategyA StrategyB StrategyC 都是具體子類,實現抽象算法接口方法
*
*
*/
public abstract class StrategyTemplate {
public abstract void AlgorithmInterface(); //算法接口
}
class ConcreteStrategyA extends StrategyTemplate{
@Override
public void AlgorithmInterface()
{
System.out.println("算法A");
}
}
class ConcreteStrategyB extends StrategyTemplate{
@Override
public void AlgorithmInterface()
{
System.out.println("算法B");
}
}
class ConcreteStrategyC extends StrategyTemplate{
@Override
public void AlgorithmInterface()
{
System.out.println("算法C");
}
}
/**
* 具體操作類 用一個具體策略來配置, 維護 一個對 Strategy對象的引用
*
*/
class Context
{
private StrategyTemplate strategy = null;
public Context(StrategyTemplate strategy) { //初始化時,傳入具體的策略對象,不要死板,具體問題具體對待,我們也可以傳入別的參數進行一個判斷,維護對 Strategy對象的引用
this.strategy = strategy;
}
public void ContextInterface() //根據具體的策略對象,調用其算法的方法
{
strategy.AlgorithmInterface();
}
}
那么我們再來看一個具體的例子:商城策略模式
/**
* 現金收費抽象父類及其子類
* 正常收費子類 買了多少錢要多少錢
* 打折收費子類 打 n 折 0<n<10
* 返利收費子類 滿 n 返 m n > m n , m ∈ N
*
*/
public abstract class CashSuper {
public abstract double acceptCash(double money);
}
class CashNormal extends CashSuper{ //正常收費
@Override
public double acceptCash(double money)
{
return money;
}
}
class CashRebate extends CashSuper //打折收費
{
private double moneyRebate = 1;
public CashRebate(String moneyRebate)
{
this.moneyRebate = Double.parseDouble(moneyRebate);
}
@Override
public double acceptCash(double money)
{
return money * moneyRebate;
}
}
class CashReturn extends CashSuper //滿多少返多少收費
{
private double moneyCondition = 0; //滿多少
private double moneyReturn = 0; //送多少
public CashReturn(double moneyCondition, double moneyReturn)
{
this.moneyCondition = moneyCondition;
this.moneyReturn = moneyReturn;
}
@Override
public double acceptCash(double money)
{
double res = money;
int n = (int) money / (int) moneyCondition;
money -= n*moneyReturn;
return money;
}
}
/**
* Context類 方法的集合
*
*/
class CashContext{
private CashSuper cs = null;
public CashContext(String type)
{
switch (type)
{
case "正常收費":
cs = new CashNormal();
break;
case "滿300返100":
cs = new CashReturn(300,100);
break;
case "打八折":
cs = new CashRebate("0.8");
break;
}
}
public double GetResult(double money)
{
return cs.acceptCash(money);
}
}
下面就是一個main函數
public class StrategyTest {
public static void main(String[] args) {
CashContext cashContext = new CashContext("正常收費");
System.out.println("1000元正常收費:"+cashContext.GetResult(1000));
cashContext = new CashContext("打八折");
System.out.println("1000元打八折:"+cashContext.GetResult(1000));
cashContext = new CashContext("滿300返100");
System.out.println("1000元滿三百減一百:"+cashContext.GetResult(1000));
}
}
運行結果:
1000元正常收費:1000.0
1000元打八折:800.0
1000元滿三百減一百:700.0