C# 继承和新关键字
当我添加新关键字或删除关键字时,事情的行为都是一样的!new关键字应该重新实现基类的方法并将其隐藏,以下是示例:C# 继承和新关键字,c#,.net,inheritance,overriding,new-operator,C#,.net,Inheritance,Overriding,New Operator,当我添加新关键字或删除关键字时,事情的行为都是一样的!new关键字应该重新实现基类的方法并将其隐藏,以下是示例: class Program { static void Main(string[] args) { BaseClass bc = new BaseClass(); DerivedClass dc = new DerivedClass(); BaseClass bcdc =
class Program
{
static void Main(string[] args)
{
BaseClass bc = new BaseClass();
DerivedClass dc = new DerivedClass();
BaseClass bcdc = new DerivedClass();
Console.WriteLine("bc __________________");
bc.Method1();
bc.Method2();
Console.WriteLine("dc __________________");
dc.Method1();
dc.Method2();
Console.WriteLine("bcdc __________________");
bcdc.Method1();
bcdc.Method2();
Console.ReadLine();
}
}
class BaseClass
{
public void Method1()
{
Console.WriteLine("Base - Method1");
}
public void Method2()
{
Console.WriteLine("Base - Method2");
}
}
class DerivedClass : BaseClass
{
public new void Method1()
{
Console.WriteLine("Derived - Method1");
}
public void Method2()
{
Console.WriteLine("Derived - Method2");
}
}
bcdc的输出将显示
基本方法1
调用bcdc.Method1()时;它不是应该显示“派生方法1”吗?如果不是,请向我解释原因。(当使用Virtual/override时,它可以很好地工作,我很满意),但是使用new关键字时,它的工作方式与使用它或不使用它类似。使用将简单地隐藏基本实现,它不会覆盖它。不使用new
修饰符做同样的事情,但是隐式地
将变量定义为基类
时,是否将其初始化为派生类并不重要。您仍然只能访问基类中定义的方法
BaseClass bcdc = new DerivedClass();
Console.WriteLine("bcdc __________________");
bcdc.Method1();
bcdc.Method2();
同样,使用new
access修饰符并不会改变功能,它只为查看类实现的人提供了一个线索,让他们了解该方法应该隐藏基本实现。使用将只隐藏基本实现,而不会覆盖它。不使用new
修饰符做同样的事情,但是隐式地
将变量定义为基类
时,是否将其初始化为派生类并不重要。您仍然只能访问基类中定义的方法
BaseClass bcdc = new DerivedClass();
Console.WriteLine("bcdc __________________");
bcdc.Method1();
bcdc.Method2();
同样,使用
new
access修饰符并不会改变功能,它只为查看类实现的人提供了一个线索,让他们明白该方法应该隐藏基本实现。好吧,这正是虚拟/覆盖
和新建
之间的区别
- 在第一种情况下(
),将调用被重写的方法,而不管从哪种类型的变量调用它。这种行为有一个名字,叫做多态性,在面向对象编程中被广泛使用virtual/override
- 在第二种情况下(
),这取决于!如果变量的类型在定义new
方法之前,则从该变量调用时将调用旧方法。否则,将调用较新的方法。这被称为方法阴影(方法共享相同的名称,但它们实际上不同,而且可能不相关-这就是为什么会有不同的行为),当基类引入了一个新方法,而您的派生类已经有了该方法时,将使用该方法。要告诉C#它们的关系不是虚拟的/重写的,您可以使用new
。这通常是最好避免的new
- 这正是
虚拟/覆盖
和新
之间的区别
- 在第一种情况下(
),将调用被重写的方法,而不管从哪种类型的变量调用它。这种行为有一个名字,叫做多态性,在面向对象编程中被广泛使用virtual/override
- 在第二种情况下(
),这取决于!如果变量的类型在定义new
方法之前,则从该变量调用时将调用旧方法。否则,将调用较新的方法。这被称为方法阴影(方法共享相同的名称,但它们实际上不同,而且可能不相关-这就是为什么会有不同的行为),当基类引入了一个新方法,而您的派生类已经有了该方法时,将使用该方法。要告诉C#它们的关系不是虚拟的/重写的,您可以使用new
。这通常是最好避免的new
new
和virtual/override
是相反的关键字
:用于跨继承层次结构中的一系列类型声明具有单个实现的单个方法virtual/override
:用于显式地声明一个新方法,与具有相同签名的所有其他方法分开。没有new
也有同样的效果,只是隐式的new
在这种情况下,代码没有
virtual
方法,因此编译器静态绑定到由调用它的引用类型指定的方法,在某些方面new
和virtual/override
是相反的关键字
:用于跨继承层次结构中的一系列类型声明具有单个实现的单个方法virtual/override
:用于显式地声明一个新方法,与具有相同签名的所有其他方法分开。没有new
也有同样的效果,只是隐式的new
虚拟
方法,因此编译器静态绑定到由调用它的引用类型指定的方法请查看,第56页:
声明在声明所属的声明空间中定义名称。除了重载成员(§3.6)之外,在声明空间中有两个或多个引入同名成员的声明是编译时错误
当您将变量声明为特定类型时,成员查找将使用该类型的声明空间完成,被重写的成员除外。由于您尚未重写方法1
成员,因此会发现并使用基类的成员。请查看,第56页:
声明在声明所属的声明空间中定义名称。除了重载成员(§3.6)之外,如果有两个或多个声明在声明中引入具有相同名称的成员,则是编译时错误