策略模式,将函数传递给父方法
Strategy pattern, pass function into parent method
我想实现类似策略模式的东西。我在 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);
}
}
我对功能的理解是否正确?
正确使用策略模式意味着上下文(在您的情况下 class A
)和策略(在您的情况下 Function
的实现)之间的聚合。
你可以在下图中看到关系(取自四人帮书,Design patterns: elements of reusable object-oriented software)。
下面我对您的问题应用了传统的策略模式方法。在这种情况下,我已经做到了 Function.apply(AbstractForm)
returns 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
}
}
在这种情况下,不需要扩展 class A
,因为我们可以使用 setStrategy(Function)
注入我们的策略 (Function
)。但是,我们总是可以将 A
扩展到具有预定义策略的伟大对象。
例如:
public class B extends A {
public B() {
setStrategy((form) -> null); // implement your concrete strategy here
}
}
使用工厂方法
由于可能需要获取数据的策略,并且可能没有 'default' 可以使用并且可能永远不会更改,因此可以使用工厂方法模式来强制创建产品(Function
).注意 class A
现在是抽象的并且包含一个工厂方法 createFunction()
然后在子 class 中实现(例如 B
)以创建 Function
.
工厂方法模式的设计可以在下面的 UML 中看到。在这种情况下,我们的产品现在是我们以前的策略 (Function
),而创建者是 class A
,而 ConcreteCreator 是 class B
。
创作者
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
}
}
在这种情况下,Product 是固定的且不可更改,但这可以通过将两个模式混合在一起并从第一个示例中的 class A
再次包含 setStrategy(Function)
来克服.
我想实现类似策略模式的东西。我在 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);
}
}
我对功能的理解是否正确?
正确使用策略模式意味着上下文(在您的情况下 class A
)和策略(在您的情况下 Function
的实现)之间的聚合。
你可以在下图中看到关系(取自四人帮书,Design patterns: elements of reusable object-oriented software)。
下面我对您的问题应用了传统的策略模式方法。在这种情况下,我已经做到了 Function.apply(AbstractForm)
returns 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
}
}
在这种情况下,不需要扩展 class A
,因为我们可以使用 setStrategy(Function)
注入我们的策略 (Function
)。但是,我们总是可以将 A
扩展到具有预定义策略的伟大对象。
例如:
public class B extends A {
public B() {
setStrategy((form) -> null); // implement your concrete strategy here
}
}
使用工厂方法
由于可能需要获取数据的策略,并且可能没有 'default' 可以使用并且可能永远不会更改,因此可以使用工厂方法模式来强制创建产品(Function
).注意 class A
现在是抽象的并且包含一个工厂方法 createFunction()
然后在子 class 中实现(例如 B
)以创建 Function
.
工厂方法模式的设计可以在下面的 UML 中看到。在这种情况下,我们的产品现在是我们以前的策略 (Function
),而创建者是 class A
,而 ConcreteCreator 是 class B
。
创作者
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
}
}
在这种情况下,Product 是固定的且不可更改,但这可以通过将两个模式混合在一起并从第一个示例中的 class A
再次包含 setStrategy(Function)
来克服.