策略模式(Strategy):它定義了演算法家族,分別封裝起來,讓它們之間可以互相替換,此模式讓演算法的變化不會影響到使用演算法的客戶。 ——《大話設計模式》 策略模式主要用來解決當有多種相似演算法的時,使用if...else產生的難以維護的問題。它主要由三部分組成:Strategy介面、具體的Strate ...
策略模式(Strategy):它定義了演算法家族,分別封裝起來,讓它們之間可以互相替換,此模式讓演算法的變化不會影響到使用演算法的客戶。
——《大話設計模式》
策略模式主要用來解決當有多種相似演算法的時,使用if...else產生的難以維護的問題。它主要由三部分組成:Strategy介面、具體的Strategy類以及用來改變和執行策略的Context類。
接下來將以一個超市選擇優惠活動的例子實現策略模式。
Strategy介面
interface Strategy {
/**
* 優惠活動
* @param money 原價
* @returns 現價
*/
discount(money: number): number;
}
具體的優惠策略
// 滿減優惠
class FullAndReduceStrategy implements Strategy {
// 滿足條件的金額
private conditionMoney: number;
// 減少的金額
private reduceMoney: number;
constructor(money: number, returnMoney: number) {
this.conditionMoney = money;
this.reduceMoney = returnMoney;
}
public discount(money: number): number {
let result: number;
if (money >= this.conditionMoney) {
result =
money - Math.floor(money / this.conditionMoney) * this.reduceMoney;
}
return result;
}
}
// 現金折扣
class CashRebateStrategy implements Strategy {
// 折扣值
private moneyRabte: number;
constructor(moneyRabte: number) {
this.moneyRabte = moneyRabte;
}
discount(money: number): number {
return money * this.moneyRabte;
}
}
Context類
setStrategy
方法用來控制要使用的策略,execute
方法用來執行策略。
class Context {
private strategy: Strategy;
private money: number;
constructor(money: number) {
this.money = money;
}
// 設置優惠策略
public setStrategy(strategy: Strategy): void {
this.strategy = strategy;
}
// 執行策略
public execute(): number {
return this.strategy.discount(this.money);
}
}
測試
const context: Context = new Context(100);
context.setStrategy(new FullAndReduceStrategy(50, 2));
console.log(context.execute()); // 96
context.setStrategy(new CashRebateStrategy(0.5));
console.log(context.execute()); // 50