【问题标题】:C# - Complete return from base methodC# - 从基本方法完全返回
【发布时间】:2012-06-02 15:56:12
【问题描述】:

我有一个虚拟基方法void Action(),它在派生类中被覆盖。

行动的第一步是致电base.Action()。如果基本方法中出现某种情况,我不希望处理派生方法的其余部分。

我想知道是否有关键字或设计模式可以让我从基方法中退出派生方法。

目前我正在考虑将 void 更改为 bool 并将其用作流控制,但我想知道是否还有其他设计模式可以使用。

【问题讨论】:

  • 不,这不是错误情况,因此异常不会起作用。
  • 抱歉增益(删除了之前关于不需要解决方案的帖子),我仍然需要解决方案,系统变得相当复杂。基本上在代码的其他地方有一个 credits_available 变量。如果没有可用的积分,我希望能够禁用基类中的所有操作。我希望能够在派生类不必复制代码的情况下做到这一点。

标签: c# inheritance methods base derived


【解决方案1】:

不要将它与 void 返回的类型一起使用,但可以这样做,比如 bool

public class Base
{
    public virtual bool Action()
    {
       ..
       return boolean-value.
    }
}

public class Child : Base
{
    public override bool Action()
    {
       if(!base.Action()) 
         return false;

       ....
       return boolean-value;
    }
}

或者,如果这是一个例外情况,请提出一个例外,就像其他人建议的那样。

【讨论】:

  • 这有点混乱,因为它向类的使用者暴露了不必要的实现。
  • @Slugart:你在说什么实现?
  • 对不起意味着实现细节 - Action 现在暴露了它返回 bool 的事实。这对派生类的消费者意味着什么?
  • 什么意思其实,可以在documentation/cmets给函数指定。如果这是一个好的或坏的设计,取决于具体的程序架构/设计。我不知道该代码在什么context中使用,所以只提供一种可能的解决方案。
  • 这是一个好的或坏的设计还取决于它是否尊重面向对象设计的原则,其中之一就是封装。我只是想指出这个设计泄露了一个实现细节。
【解决方案2】:

在基方法中抛出异常。它将退出调用它的每个方法,直到被捕获。

【讨论】:

  • 在被频繁调用的方法中抛出异常并不是一个好主意。
  • @Mert:在异常情况下这是个好主意,但在大多数情况下对控制流来说是个坏主意。
  • @Mert:经常抛出异常不好,但是正如OP所说,只有在“情况”时才抛出异常。并非每次调用该方法时都会发生这种情况,因为正常流程是在派生方法中运行其余代码。
  • @Guffa:在这种情况下,“情况”不是错误。 “目前我正在考虑将 void 更改为 bool 并将其用作流量控制”,他正在寻找一种在流量控制中使用它的方法,并且流量控制条件即使不是每次都会发生非常频繁。
  • @Guffa:这是我的解释?您如何解释“不,这不是错误情况,因此异常不起作用 – Talib”?讨论结束。
【解决方案3】:

这是一个错误“情况”吗?如果是这样,只需让它抛出异常,不要在覆盖范围内捕获异常。

如果不是错误情况,那么使用返回类型听起来确实是一种前进的方式,但它可能不适合您的上下文 - 我们真的不知道您想要实现什么。

另一种选择是使用template method pattern

public abstract class FooBase
{
    public void DoSomething()
    {
        DoUnconditionalActions();
        if (someCondition)
        {
            DoConditionalAction();
        }
    }

    protected abstract void DoConditionalAction();
}

如果您不想将基类抽象化,您可以将其设为受保护的虚方法,该方法在基类中什么都不做,并在适当的情况下在派生类中被覆盖。请注意,DoSomething 在此处不是虚拟的。

如果这些选项听起来都不合适,您需要向我们提供有关您想要实现的目标的更具体信息。

【讨论】:

    猜你喜欢
    • 2020-11-28
    • 2016-03-06
    • 1970-01-01
    • 2020-02-05
    • 1970-01-01
    • 2014-01-16
    • 1970-01-01
    • 2019-07-20
    • 1970-01-01
    相关资源
    最近更新 更多