在类层次结构中定义方法时,C#中的override
和new
关键字有什么区别?
答案 0 :(得分:82)
以下页面很好地总结了您的问题。
Knowing When to Use Override and New Keywords
<强>摘要强>
覆盖:在派生类中重写基类的方法时,使用派生类中的版本,即使调用代码没有“知道”该对象是派生类的一个实例。
新:如果使用new关键字而不是override,派生类中的方法不会覆盖基类中的方法,它只会隐藏它。
如果未指定new或覆盖,则结果输出与指定new相同,但您也会收到编译器警告(因为您可能不知道您正在隐藏方法基类方法,或者你可能想要覆盖它,只是忘了包含关键字)。
覆盖:与基类中的virtual / abstract / override类型的方法一起使用
新:当基类未将方法声明为virtual / abstract / override
时答案 1 :(得分:64)
new
将使用一个全新的方法(可能具有或不具有相同的签名)来遮蔽该方法,而不是覆盖它(在这种情况下,新方法必须具有相同的签名),这意味着多态性赢得了& #39;工作。例如,您有这些类:
class A {
public virtual int Hello() {
return 1;
}
}
class B : A {
new public int Hello(object newParam) {
return 2;
}
}
class C : A {
public override int Hello() {
return 3;
}
}
如果你这样做:
A objectA;
B objectB = new B();
C objectC = new C();
Console.WriteLine(objectB.Hello(null)); // 2
Console.WriteLine(objectC.Hello()); // 3
objectA = objectB;
Console.WriteLine(objectA.Hello()); // 1
objectA = objectC;
Console.WriteLine(objectA.Hello()); // 3
由于您可以使用new
定义新的方法签名,因此编译器无法知道A
的实例实际上是B
的实例并且是新的方法B
定义应该可用。当父对象的方法,属性,字段或事件未使用new
声明时,可以使用virtual
,并且由于缺少virtual
,编译器赢了&#39}。 t“查找”继承的方法。但是,对于virtual
和override
,它可以正常工作。
我强烈建议你避免new
;充其量,这是令人困惑的,因为你正在定义一个名称可以被识别为其他东西的方法,最糟糕的是,它可以隐藏错误,引入看似不可能的错误,并使扩展功能变得困难。
答案 2 :(得分:8)
看起来像一个老问题,让我尝试不同的答案:
new
:正如名称所示,它是继承层次结构系列中的新成员,它将用作进一步向下链的基本成员(如果标记为虚拟)。
override
:这意味着我不接受我父类的成员实施,我将采取不同的做法。
答案 3 :(得分:2)
考虑以下类层次结构:
using System;
namespace ConsoleApp
{
public static class Program
{
public static void Main(string[] args)
{
Overrider overrider = new Overrider();
Base base1 = overrider;
overrider.Foo();
base1.Foo();
Hider hider = new Hider();
Base base2 = hider;
hider.Foo();
base2.Foo();
}
}
public class Base
{
public virtual void Foo()
{
Console.WriteLine("Base => Foo");
}
}
public class Overrider : Base
{
public override void Foo()
{
Console.WriteLine("Overrider => Foo");
}
}
public class Hider : Base
{
public new void Foo()
{
Console.WriteLine("Hider => Foo");
}
}
}
上述代码的输出必须是:
Overrider => Foo
Overrider => Foo
Hider => Foo
Base => Foo
- 子类
overrides
是一个虚拟方法,应用override modifier
:- 如果您想故意
hide
成员,在这种情况下,您可以将new modifier
应用于子类中的成员。The new modifier does nothing more than suppress the compiler warning that would otherwise result
答案 4 :(得分:1)
override
允许您覆盖基类中的虚方法,以便您可以放入不同的实现。new
将隐藏基类中的非虚方法。
答案 5 :(得分:0)