【问题标题】:State Design Pattern: How to avoid code duplication when using entry() and exit()?状态设计模式:使用 entry() 和 exit() 时如何避免代码重复?
【发布时间】:2020-08-04 11:03:46
【问题描述】:

情况:我的状态有一个 entry() 和 exit() 方法,每次状态转换时都需要调用它们。为了确保这一点,我在 State 中使用了一个 changeState() 方法,其中包含必要的过程。上下文每次使用涉及状态机的操作时都会调用它。然而,问题是我每次添加新方法时都需要调用 state.changeState() ,并且我确信有一种方法可以避免代码重复。以下是进一步说明的代码

class Context {
    State state;

    void method1() {
        state.method1();
        state.changeState();
    }

    void method2() {
        state.method2();
        state.changeState(); // Code duplication!!
}

abstract class State {
    Context context;
    State next;

    void changeState() {
        this.exit();
        next.entry();
        context.setState(next);
    }
    // other necessary methods
}

class ConcreteState extends State {
    void method1() {
        // do something
        next = AnotherConcreteState;
    }
    void entry() {/*do something */};
    void exit() {/*do something */};
}

如果我想在 Context 中添加额外的方法,如何避免在新方法中每次调用 state.changeState() 的代码重复?

【问题讨论】:

    标签: java design-patterns code-duplication state-pattern


    【解决方案1】:

    你很亲密。 changeState 方法属于Context 类,而不是State 类。这是a good article on the topic。请注意,类图显示Document(上下文)类中的changeState

    为了更简洁,changeState 可以将next 状态作为参数。像这样:

    class Context {
      State state;
    
      void method1() {
        state.method1();
      }
    
      void changeState(next) {
        state.exit();
        this.state = next;
        state.enter();
      }
    }
    
    abstract class State {
      Context context;
    
      // other methods
    }
    
    class ConcreteState extends State {
      void method1() {
        // do something
        context.changeState(AnotherConcreteState);
      }
    
      void enter() { /* do something */ }
      void exit() { /* do something */ }
    }
    

    现在,随着您向Context 添加更多方法,Context 中没有重复。它看起来像这样:

    class Context {
      State state;
    
      void method1() {
        state.method1();
      }
    
      void method2() {
        state.method2();
      }
    
      void changeState(next) {
        state.exit();
        this.state = next;
        state.enter();
      }
    }
    
    abstract class State {
      Context context;
    
      // other methods
    }
    
    class ConcreteState extends State {
      void method1() {
        // do something
        context.changeState(AnotherConcreteState);
      }
    
      void method2() {
        // do something else
        context.changeState(YetAnotherConcreteState);
      }
    
      void enter() { /* do something */ }
      void exit() { /* do something */ }
    }
    

    【讨论】:

      猜你喜欢
      • 2023-01-14
      • 2022-01-23
      • 2021-11-07
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多