【问题标题】:If a virtual method is declared abstract如果虚方法被声明为抽象的
【发布时间】:2014-10-17 19:42:23
【问题描述】:

我的朋友问我 abstract 方法是否可以有 virtual 修饰符。我说,。 因为,抽象方法隐含也是虚拟方法,它不能有修饰符 virtual。

但是在阅读one of the MSDN articles时,我看到了这个:

... 如果一个 virtual 方法被声明为 abstract,它对任何人来说仍然是虚拟的 类继承自抽象类。继承一个类 抽象方法无法访问原始实现 方法——在前面的例子中,类 F 上的 DoWork 不能调用 DoWork 在 D 类上。这样,抽象类可以强制派生类 为虚拟方法提供新的方法实现......

我无法正确理解第一句话。你能解释一下他们想说什么吗?

谢谢。

【问题讨论】:

  • 第一句只是意味着abstract关键字在“虚拟性”方面没有任何改变,即该方法仍然是virtual,即它仍然会表现出多态性。
  • @BartoszKP 在阅读了 Heinzi 的回答和您的评论后,我明白了。谢谢。
  • 这可能会让你感兴趣:ericlippert.com/2011/02/07/strange-but-legal
  • @EricLippert 感谢您的链接。这真的很明智。也很有趣。

标签: c# oop inheritance polymorphism


【解决方案1】:

当您直接查看引用段落上方的代码示例时会更清楚:

public class D
{
    public virtual void DoWork(int i)
    {
        // Original implementation.
    }
}

public abstract class E : D
{
    public abstract override void DoWork(int i);
}

虚拟方法D.DoWorkE 继承,并且在那里声明为抽象的。该方法仍然是虚拟的,它也刚刚变成了抽象

正如您所说的那样,抽象方法始终是虚拟的。如果你的朋友仍然不相信,这里有一个official quote

抽象方法是隐含的虚拟方法。

【讨论】:

  • 方法还是虚的,也只是抽象了。这句话我看懂了。非常感谢。
  • C# 关键字 abstract(应用于方法)在 VB.NET 中被命名为 MustOverride。我一直认为这是一个笨拙的名字,但它实际上非常适合此处显示的非常具体的场景(其中 virtual 方法在派生类中再次使用 abstract)。
  • @stakx:确实。 virtual 被命名为 OverridableMustOverride 暗示 Overridable 是完全合理的。
【解决方案2】:

抽象类可以用abstract 覆盖virtual 成员:

public class B
{
    public virtual void M() { }
}
public abstract class D : B
{
    public abstract override void M();
}
public abstract class D2 : D
{
    public override void M() { }
}

这句话说D2 必须 覆盖void M(),因为它在D 中被声明为抽象的。如果它被声明为D2 : B,这将是可选的,但就目前而言,D2 必须遵守D 中指定的合同,但M() 的行为也会像任何其他成员一样覆盖“正常”虚拟成员,因为M() 既是虚拟的又是抽象的。

【讨论】:

    猜你喜欢
    • 2011-07-18
    • 1970-01-01
    • 1970-01-01
    • 2011-04-06
    • 1970-01-01
    • 2015-02-28
    • 2016-05-10
    • 2011-01-23
    • 2012-10-31
    相关资源
    最近更新 更多