寻找更好的方法来扩展方法

Looking for a better way to extend methods

我正在使用 Unity 开发一个业余爱好项目。我的角色有 MonoBehaviour 脚本,角色的每个行为都使用组件 objects。当我创建新角色时,我会从基础 class 继承一个新的 class,无论哪个组件的行为不同。

当某些触发器发生时,我通过调用基 class 公开的 Reset() 方法将字符发送回其初始状态,该方法将字段设置回其初始值。我想知道如何通过继承链向下发送该调用。现在,基础 class 有一个受保护的虚拟 ChildReset(),它在 Reset() 中被调用并且默认情况下不执行任何操作。如果 child classes 有要重置的字段,它们会覆盖此方法。感觉这样做真的很尴尬。

我喜欢实现类似于 messaging system Unity 使用的东西的想法。如果单一行为不使用 Update() 消息,那么 class 就不会定义更新。它消除了不必要的呼叫。我不知道我会怎么做。

非常感谢对此投入的任何想法!我已经在下面写下了我的项目的结构方式,以防这些细节对答案有用。

public class Character : MonoBehaviour
{
    private Motion motionController;
    private Interaction characterInteractionController;
    //etc

    private void Update()
    {
        motionController.DoStuff();
        characterInteractionController.DoStuff();
    }

    private void Reset()
    {
        motionController.Reset();
        characterInteractionController.Reset();
    }

    private void OnEnable() => ResetTrigger.OnReset += Reset;
    private void OnDisable() => ResetTrigger.OnReset -= Reset;
}

public class Motion : Component {}
public class Interaction : Component {}

public abstract class Component
{
    public void Reset() 
    { 
        /* set fields to default values */ 
        ChildReset();
    }
    
    protected virtual void ChildReset() { }
    public abstract void DoStuff();
}

无需通过继承链向下发送调用。您没有两个不同的对象。子 class 的对象包含在基 class 中声明的所有内容。为什么不直接将 Reset() 虚拟化?

public abstract class Character : MonoBehaviour
{
    public virtual void Reset()
    {
        ...
    }
}

public class ChildCharacter : Character
{
    // If ChildCharacter has stuff to reset, override this method, otherwise don't!
    public override void Reset()
    {
        base.Reset(); // Call this to reset stuff from the base class.

        //TODO: reset child stuff.
    }
}

如果 Reset 在子 class 中被覆盖,那么调用 Reset 将调用 ChildCharacter.Reset(),即使调用静态类型为 Character 的变量也是如此.

    Character c = new ChildCharacter();
    c.Reset(); // calls ChildCharacter.Reset() when overridden

如果 Reset 未在子 class 中被覆盖,则即使在 ChildCharacter 上调用 Reset 也会调用 Character.Reset()

    ChildCharacter child = new ChildCharacter();
    child.Reset(); // calls Character.Reset() when not overridden.