c# - 虚拟方法可以中止覆盖它的抽象方法的执行吗?

标签 c# overriding state-machine

我正在为游戏 AI 实现一个状态机,其中一个状态 —EatState — 必须可以从几乎所有其他状态访问,并且优先于其他状态。我没有在所有状态中定义此转换,而是考虑在父类(super class) BaseState 中实现它,所有其他状态都从该父类(super class)扩展。

BaseState有4个子类重写的抽象方法,分别是

  1. 输入()
  2. UpdateLogic() -> 检查从一种状态转换到另一种状态的条件...
  3. UpdatePhysics() -> 应用运动和其他
  4. 退出()

如果我在父类(super class)中实现对 EatState 转换的检查,然后调用子类的特定检查,我发现的问题是后者的结果覆盖 在父类(super class)中获得的:

public class BaseState {
   public virtual void UpdateLogic() {
      // Let's imagine the condition is met and the state is changed
      if (someCondition){
         changeState("EatState");
      }
   }
}


public class MoveState : BaseState {
   public override void UpdateLogic() {
      base.UpdateLogic();
      // But here the condition is also met, so the state is re-changed.
      if (someOtherCondition){
         changeState("FightState");
      }
   }
}

我意识到我可以将优先状态检查移至方法的底部,以便覆盖子类的结果:

public class MoveState : BaseState {
   public override void UpdateLogic() {
      if (someOtherCondition){
         changeState("FightState");
      }
      base.UpdateLogic();
   }
}

或者我可以使子类中的检查更加严格,但这个问题让我想知道这一点:

一旦在父类(super class)中执行基本虚拟方法,是否有办法避免执行重写方法?我正在寻找类似 return 语句的东西,它可以以某种方式从父类(super class)传播到子类并中止后者的执行。

最佳答案

您可以通过返回 bool 而不是 void 来指示是否使用了基类行为来控制此行为。

public class BaseState
{
    public virtual bool UpdateLogic()
    {
        // Let's imagine the condition is met and the state is changed
        if (someCondition)
        {
            changeState("EatState");
            return true;
        }
        
        return false;
    }
}

public class MoveState : BaseState
{
    public override bool UpdateLogic()
    {
        var wasUpdatedInBase = base.UpdateLogic();
        // But here the condition is also met, so the state is re-changed.
        if (!wasUpdatedInBase && someOtherCondition)
        {
            changeState("FightState");
        }
    }
}

关于c# - 虚拟方法可以中止覆盖它的抽象方法的执行吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/73156051/

相关文章:

c# - 您将如何更改我用 C# 编写的 Heartbeat 进程?

javascript - MVC C# 将参数传递给 VIA ActionLink 到 Controller

c# - 如何消除 "else-if"语句

c# - DataGrid 列绑定(bind)到 List 的项目

python - 覆盖 __hash__ 后哈希值相同但对象不同

c++ - 如果 QStateMachine 中的转换成功,则从类发出信号

java - 在 java 或状态机中使用枚举进行电子邮件验证

java - 如何扩展 jar 文件中的类?

delphi - 为什么编译器给我这个错误: Declaration of 'GetItem' differs from previous declaration?

ruby - 这些方法命名方法中哪种更好,为什么?