概念
ポリシーパターンとも呼ばれる戦略パターン。クラスまたはそのアルゴリズムの動作を実行時に変更できます。このタイプの設計パターンは行動パターンです。
戦略モードには通常、主に3つの役割が含まれます。
- コンテキスト:戦略を操作し、戦略とアルゴリズムへのクライアントの直接アクセスを保護し、可能な変更をカプセル化するために使用されるコンテキスト環境
- 抽象戦略(戦略):戦略またはアルゴリズムの動作を規定します
- 具体的な戦略(ConcreteStrategy):戦略またはアルゴリズムの具体的な実現
成し遂げる
次に、例として支払い方法のシナリオを取り上げます
1.抽象的な戦略を作成する
public abstract class Payment {
abstract String getName();
}
2.特定の戦略を作成します
public class AliPay extends Payment {
@Override
String getName() {
return "欢迎使用支付宝支付";
}
}
public class WeChatPay extends Payment{
@Override
String getName() {
return "欢迎使用微信支付";
}
}
3.コンテキストを作成します
public class PayStrategy {
public static final String ALI_PAY="AliPay";
public static final String WECHAT_PAY="WeChatPay";
public static final String DEFAULT="AliPay";
public static Map<String ,Payment> map=new HashMap<String ,Payment>();
static {
map.put(ALI_PAY,new AliPay());
map.put(WECHAT_PAY,new WeChatPay());
}
public static Payment get(String name){
if (!map.containsKey(name)){
return map.get(DEFAULT);
}
return map.get(name);
}
}
4.テスト
public class StrategyTest {
public static void main(String[] args) {
Payment pay=PayStrategy.get(PayStrategy.ALI_PAY);
System.out.println(pay.getName());
}
}
動作結果:
使用するシーン
- 同じタイプの問題に対処する方法はたくさんあり、それぞれが独立して問題を解決できます。
- システムは、いくつかのアルゴリズムの1つを動的に選択する必要があります
SpringFrameworkでのアプリケーション
Spring DIプロセスでは、初期化時に戦略モードが採用されます。
InstantiationStrategyインターフェースがあります
public interface InstantiationStrategy {
Object instantiate(RootBeanDefinition bd, @Nullable String beanName, BeanFactory owner)
throws BeansException;
Object instantiate(RootBeanDefinition bd, @Nullable String beanName, BeanFactory owner,
Constructor<?> ctor, @Nullable Object... args) throws BeansException;
Object instantiate(RootBeanDefinition bd, @Nullable String beanName, BeanFactory owner,
@Nullable Object factoryBean, Method factoryMethod, @Nullable Object... args)
throws BeansException;
}
また、CglibSubclassingInstantiationStrategyとSimpleInstantiationStrategyの2つの戦略実装クラスがあります。UML
クラス図は次のとおりです
。CglibSubclassingInstantiationStrategy戦略クラスはSimpleInstantiationStrategyクラスを継承していることがわかりました。これは、実際の使用では、複数の戦略も継承して使用できることを示しています。
総括する
利点
- 優れたスケーラビリティ、複合開閉原理
- if ... else、switch ... caseなどの複数の条件付き判断の使用は避けてください
- アルゴリズムは自由に切り替えることができます
不利益
- すべての戦略クラスを公開する必要があります
- 多くの戦略クラスを生成します