为什么在c#的继承方法中使用override而不是function

时间:2014-01-09 06:09:15

标签: c# oop inheritance

我想知道虽然继承可以用来继承派生类中的属性和方法。

为什么我们不在派生类中编写函数而是将它们声明为覆盖。

以下示例将详细解释我的问题。

class Net
{
    public virtual void Act()
    {
    }
}

class Perl : Net
{
    public override void Act()
    {
    Console.WriteLine("Perl.Act");
    }
}

class Python : Net
{
    public override void Act()
    {
    Console.WriteLine("Python.Act");
    }
}
// Use base class and derived types in a List.
List<Net> nets = new List<Net>();
nets.Add(new Perl());
nets.Add(new Python());

// Call virtual method on each instance.
foreach (Net net in nets)
{
    net.Act();
}

在上面的示例中,act函数可以声明为“NEW”函数为什么我们应该选择覆盖基函数?

  

编辑:假设我有一个案例如下

class Net
{
    public virtual void Act()
    {
    }

    public virtual void secondMethod()
    {
    }
}

class Perl 
{
    public override void Act()
    {
        Console.WriteLine("Perl.Act");
    }

    public override void secondMethod()
    {
        Console.WriteLine("Perl.Act");
    }
}

class Python 
{
    public new void Act()
    {
        Console.WriteLine("Python.Act");
    }

    public override void secondMethod()
    {
        Console.WriteLine("Perl.Act");
    }
}

那我该怎么办? 在上面的例子中,我希望继承基类,但我实现的功能可能不同。 在这种情况下,我应该使用覆盖或写一个完全不同的方法。

3 个答案:

答案 0 :(得分:4)

因为在您的基类上没有virtual方法,您将无法使用循环调用Act

foreach (Net net in nets)
{
    net.Act();
}

并且foreach不是唯一可以使用它的地方。想象一下,您有一个名为Foo的方法,它将Net实例作为参数:

public static void Foo(Net net)
{
    net.Act();
}

您仍然可以将PythonPerl传递给该方法,并且他们都将执行自己的Act方法逻辑。

virtual在您想要提供一些基本的默认功能并且能够在派生类中默认override的任何地方都很有用。

您应该阅读Knowing When to Use Override and New Keywords (C# Programming Guide)

答案 1 :(得分:3)

new关键字用于方法隐藏,主要用于版本控制目的,但请注意,这两种方法在派生类中仍然可用!并且可以使用简单的cast访问。但另一方面,使用方法覆盖,您可以覆盖行为(这就是我们所说的多态),因此在派生类中,重写的方法将完全替换基本方法,因此无法访问通过派生类的实例,即使对基类进行向上转换!因为虚方法被重写方法替换。 让我用一个例子向你展示这个概念:

public class Base
{
    public virtual void VirtualMethod() { }
    public void NewMethod() { }
}

public class Derived : Base
{
    public override void  VirtualMethod() { }
    public new void NewMethod() { }
}

...

Base derived = new Derived();
derived.VirtualMethod(); // Derived.VirtualMethod()
derived.NewMethod(); // Base.NewMethod()
((Derived)derived).NewMethod(); // Derived.NewMethod()

答案 2 :(得分:1)

  

在上面的示例中,act函数可以声明为“NEW”函数为什么我们应该选择覆盖基函数

继承是指在必要时使用基类提供的额外功能。如果你不想使用基类的功能,为什么你会首先继承?