模式避免重复处理块

时间:2015-01-20 15:09:24

标签: java oop design-patterns

我有一个班级:

public class VisitorProcessing {
    public void visit(EventA eventA){
           if(condition1....)
                // Do somethings 1
           else{
               if(condition2){
               // Do something 2
               }
               else{
               // Do something 3
               }
           } 
    }
    public void visit(EventB eventB){
           if(condition1....)
                // Do somethings 4
           else{
               if(condition2){
               // Do something 5
               }
               else{
               // Do something 6
               }
           } 
    }
    public void visit(EventC eventC){
           if(condition1....)
                // Do somethings 7
           else{
               if(condition2){
               // Do something 8
               }
               else{
               // Do something 9
               }
           } 
    }
    public void visit(EventD eventD){
           if(condition1....)
                // Do somethings 10
           else{
               if(condition2){
               // Do something 11
               }
               else{
               // Do something 12
               }
           } 
    } 
}

所有事件对象扩展相同的父对象BasicEvent。 条件仅指向事件对象,可以从父事件计算。

我想开始重构,在一个地方对分支逻辑进行分组,因为我不确定条件。 我确定的唯一事情是处理" DoSomthings ......" 。

所以我在搜索是否有任何已知的模式来做到这一点。

提前致谢

3 个答案:

答案 0 :(得分:4)

调度方法负责正确调用方法,每次只需编写3个方法。

public interface DoSomething {
    void doSomething1();
    void doSomething2();
    void doSomething3();
}

public class VisitorProcessing {

    public void dispatch( DoSomething ds) {
        if(condition1....)
            ds.doSomething1();
       else{
           if(condition2){
               ds.doSomething2();
           }
           else{
               ds.doSomething3();
           }
       } 
    }

    public void visit(EventA eventA){
        DoSomething ds = new DoSomething()
        {
            void doSomething1() {
             // Do somethings 1
            }
            void doSomething2(){
             // Do something 2
            }
            void doSomething3(){
             // Do something 3
            }
        }
        dispatch( ds );
    }

    public void visit(EventB eventB){
        DoSomething ds = new DoSomething()
        {
            void doSomething1() {
             // Do somethings 3
            }
            void doSomething2(){
             // Do something 4
            }
            void doSomething3(){
             // Do something 5
            }
        }
        dispatch( ds );
    }
    ...
}

答案 1 :(得分:1)

您可能想查看chain-of-responsibility pattern。 从本质上讲,您有一个基于决策行事的类Handler,它包含一个类型为Handler的对象,可以在条件不满足时委派给它。例如:

public Class Handler() {
  private Handler next;

  public setNext(Handler next) {
    this.next = next;
  }

  public void action(params) {
    if(some_condition) {
      ...
    }
    else {
      if(next != null)
        next.action(params);
    }
  }
}

当然,可以而且应该扩展该类以创建不同类型的处理程序。在您的情况下,此模式的优点是您可以使用具有相同条件的相同链,并根据调用的visit方法更改操作。此外,您可以非常轻松地添加,编辑和删除条件,甚至可以在运行时修改链。

在你的情况下:

public Class Condition1 extends Handler {
  public void action(BasicEvent e) {
    if (condition1) {
      if(e instanceof EventA) // Do something 1
      if(e instanceof EventB) // Do something 4
      if(e instanceof EventC) // Do something 7
      if(e instanceof EventD) // Do something 10
    }
    else {
      if(next != null)
        next.action(BasicEvent e);
    }
  }
}

public Class Condition2 extends Handler {
  public void action(BasicEvent e) {
    if (condition2) {
      if(e instanceof EventA) // Do something 2
      if(e instanceof EventB) // Do something 5
      if(e instanceof EventC) // Do something 8
      if(e instanceof EventD) // Do something 11
    }
    else {
      if(next != null)
        next.action(BasicEvent e);
    }
  }
}

public Class ConditionElse extends Handler {
  public void action(BasicEvent e) {
    if(e instanceof EventA) // Do something 3
    if(e instanceof EventB) // Do something 6
    if(e instanceof EventC) // Do something 9
    if(e instanceof EventD) // Do something 12

    // we reached the end of the chain
  }
}

为其他条件创建类似的类(如果有的话)(尽可能多),然后形成链:

Condition1 condition_1 = new Condition1();
Condition2 condition_2 = new Condition2();
ConditionElse condition_else = new new ConditionElse();

condition_1.setNext(condition_2);
condition_2.setNext(condition_else);

然后你只需要一个visit方法:

public void visit(BasicEvent e){
  condition1.action(e);
}

我希望我能够快速概述适合您案例的模式。 instanceof部分可以用更好的方式处理,特别是如果你有超过4个子类值得重构,但我希望你能得到这个要点。

答案 2 :(得分:0)

如果您无法更改访问方法,那么您可以创建一个从每个访问方法中调用的进程(BasicEvent事件)方法。

public class VisitorProcessing {
    public void visit(EventA eventA){
           processEvent(eventA);
           //... EventA specific code goes here
    }
    public void visit(EventB eventB){
           processEvent(eventB);
           //... EventB specific code goes here
    }
    public void visit(EventC eventC){
           processEvent(eventC);
           //... EventC specific code goes here
    }
    public void visit(EventD eventD){
           processEvent(eventD);
           //... EventD specific code goes here
    } 

    private void processEvent(BasicEvent event) {
           if(condition1....)
                // Do somethings 10
           else{
               if(condition2){
               // Do something 11
               }
               else{
               // Do something 12
               }
           } 
    }
}