我有一些代码根据条件执行不同的逻辑。但是使用策略模式不允许删除条件代码?使用Google这似乎是使用策略模式的常见结果:https://www.google.ie/webhp?sourceid=chrome-instant&ion=1&espv=2&ie=UTF-8#q=removing%20if%20statements%20strategy%20pattern
例如:
class Cond {
if(cond1){
perform1
}
if(cond2){
perform1
}
}
策略模式:
interface Performer {
doWork
}
class Perform1 implements Performer {
doWork
}
class Perform2 implements Performer {
doWork
}
class Cond {
if(cond1){
new Perform1.doWork
}
if(cond2){
new Perform2.doWork
}
}
策略模式更关注开放封闭原则而不是实际删除条件代码?也不是条件码自然发生的编程?
答案 0 :(得分:0)
这对我来说并不像策略模式实现那样。我理解它是伪代码,但我不遵循它。这个例子更简单,实际上在执行策略时不需要编写条件:
// Strategy Interface
public interface CompressionStrategy {
public void compressFiles(ArrayList<File> files);
}
public class ZipCompressionStrategy implements CompressionStrategy {
public void compressFiles(ArrayList<File> files) {
// using ZIP approach
}
}
public class RarCompressionStrategy implements CompressionStrategy {
public void compressFiles(ArrayList<File> files) {
// using RAR approach
}
}
public class CompressionContext {
private CompressionStrategy strategy;
// this can be set at runtime by the application preferences
public void setCompressionStrategy(CompressionStrategy strategy) {
this.strategy = strategy;
}
// use the strategy
public void createArchive(ArrayList<File> files) {
strategy.compressFiles(files); // <-- with stragtegy set, notice that
// no conditionals are required here.
}
}
public class Client {
public static void main(String[] args)
{
CompressionContext ctx = new CompressionContext();
//we could assume context is already set by preferences
ctx.setCompressionStrategy(new ZipCompressionStrategy());
//get a list of files
...
ctx.createArchive(fileList);
}
}
答案 1 :(得分:0)
策略模式仅封装差异,您仍需要在执行期间分配正确的行为。
您可以将策略附加到请求工作的对象,而不是设置条件标志。
在这里看看如何转换具有多态性的开关:http://sourcemaking.com/refactoring/replace-conditional-with-polymorphism
答案 2 :(得分:0)
是的,条件是编程的基本和固有元素。您不能,也没有任何理由想要删除条件代码&#34;来自任何非平凡的计划。 实现条件代码有不同的方法,有些情况下有些方法优于其他方式,但坦白说,完全删除它的概念是无意义的。
策略模式只是封装 - 具体来说,它是关于封装算法:看看你给出的两个例子之间的区别。您避免删除了所有条件,两个示例中都有相同的两个if
语句。唯一的区别是,在后者中,您已将算法封装在类中。
答案 3 :(得分:0)
你可能想要一些与责任链类似的东西(c#sorry)
interface Performer {
bool CanHandle(/* criteria/lambda */);
void DoWork();
}
class Cond
{
void Do()
{
Performer strategy=strategies.Find(s=>s.CanHandle(/* condition */));
if (strategy==null) throw new NoStrategyAvailable();
strategy.DoWork();
}
}
可能不是应用最纯粹的策略模式,但是它非常易于维护:如果您使用反射从项目中获取所有策略,您只需添加一个新的策略实现,它就可以正常工作。