2017-10-17 5 views
1

戦略パターンのようなものを実装したいと思います。私はParentメソッドでロジックを一般化しているので、(キャスティングなどで)特定のロジックを親に渡す必要があります。戦略パターン、親メソッドに関数を渡す

私は以下のいるクラスは:

class A{ 
    public Object generateData(Function fetchData, AbstractForm form) 
    { 
     List<DataBean> dataBeans = (List<DataBean>) fetchData.apply(form); 
     //... 
    } 
} 

class B extends A{ 
    void someMethod(AbstractForm form){ 
     Function<AbstractForm, List<DataBean>> fetchFunction = new Function<AbstractForm, List<DataBean>>() { 
      //here goes form specific casting and other data fetch specific logic 
      return dataBeans; 
     } 
     super.generateData(fetchFunction, form); 
    } 
} 

私は正しくここに機能のアイデアを得ましたか。

+0

多分それはあなたを助けるかもしれません:Java 8の戦略デザインパターンhttp://www.baeldung.com/java-strategy-pattern –

+1

私たちはあなたがそのアイデアを正しく持っているかどうかをどのように認識するでしょうか?コードの一部を投稿することはできません... – Holger

答えて

4

戦略パターンを正しく使用することは、コンテキスト(ケースクラスA)と戦略(ケースではFunction)の間の集約を意味します。

以下の画像(Gang of Four書籍のDesign patterns: elements of reusable object-oriented softwareから取得)の関係を見ることができます。私はあなたの問題への従来のStrategyパターンのアプローチを適用した以下

Strategy pattern UML

。この場合は、Function.apply(AbstractForm)List<DataBean>を返すようにして、キャスティングの必要性を排除しました。もちろん、汎用性を利用してFunctionをより柔軟にすることができます。

戦略この場合

public interface Function { 
    List<DataBean> apply(AbstractForm form);  
} 

コンテキスト

public class A { 

    private Function fetchData; // strategy 

    public void setStrategy(Function fetchData) { // method for setting the strategy 
     this.fetchData = fetchData; 
    } 

    // precondition: fetchData != null 
    public Object generateData(AbstractForm form) { 
     List<DataBean> dataBeans = fetchData.apply(form); // using the strategy 
     return null; // whatever you want to return 
    }  
} 

、拡張クラスAは、我々の戦略(FunctionsetStrategy(Function)を使用して注入できるよう必要ありませんです。しかし、私たちは常にAを、あらかじめ定義されたストラテジーを持つオブジェクトに拡張することができます。例えば

:ファクトリメソッド

を使用して

public class B extends A { 

    public B() { 
     setStrategy((form) -> null); // implement your concrete strategy here 
    } 
} 

データをフェッチするための戦略は、おそらく必要とされ、そこに使用するために何の「デフォルト」ないかもしれないし、今までに変更されないことがありますので、 Factoryメソッドパターンを使用して、Product(Function)の作成を強制することができます。注釈クラスAは現在抽象化されており、ファクトリメソッドcreateFunction()を含み、サブクラス(例:B)に実装されてFunctionが作成されます。

ファクトリメソッドパターンのデザインは、以下のUMLで見ることができます。この場合、当社の製品は以前は戦略(Function)であり、作成者はクラスAであり、ConcreteCreatorはクラスBです。この場合

Factory method pattern UML

クリエーター

public abstract class A { 

    private Function fetchData; // product to be used 

    public class A() { 
     fetchData = createFunction(); // call factory method 
    } 

    protected abstract Function createFunction(); // factory method 

    // precondition: fetchData != null 
    public Object generateData(AbstractForm form) { 
     List<DataBean> dataBeans = fetchData.apply(form); // using the product 
     return null; // whatever you want to return 
    } 

} 

ConcreteCreator

public class B extends A { 

    @Override 
    protected Function createFunction() { 
     return (form) -> null; // return product 
    } 
} 

製品を固定し、changableないが、これは二つのパターンを混合することによって克服することができ一緒に、最初の例ではクラスAから再び10になります。

関連する問題