相同的代码,但输出不同的 C# 与使用多态性的 Java
本文关键字:Java 多态性 输出 代码 | 更新日期: 2023-09-27 18:35:27
我在玩多态概念。我认为所有OOP概念在每种语言中都是相同的(几乎)。我编译并运行了这段代码,但java和c#给出了不同的答案:
public class Employee
{
// constructor implemented
public void mailCheck()
{
Console.WriteLine("In Employee Method'n Mailing a check to "+ this.name+ " " + this.address);
}
}
public class Salary : Employee
{
//constructor implemented
public void mailCheck()
{
Console.WriteLine("Within mailCheck of Salary class ");
Console.WriteLine("Mailing check to " + getName() + " with salary " + salary);
}
}
class driver
{
static void Main(string[] args)
{
Employee e = new Salary("John Adams", "Boston, MA", 2, 2400.00);
e.mailCheck();
}
}
如果我在 java 中运行此代码,它调用工资类方法,如果我在 c# 中运行此代码,它调用员工类方法。
为什么会这样?
在 Java 中,您不必编写 @Override
即可覆盖具有相同签名的方法。默认情况下是这样的。在 C# 中并非如此,因为您必须添加前缀virtual
( public virtual void mailCheck()
) 以指示该方法将被覆盖。
这就是为什么您在两种语言之间获得不同的输出的原因。
在 C# 中,您不会重写 mailCheck
方法。因为通过像在 C# 中那样将mailCheck
重新定义为类Salary
,您只是将基类中定义的函数隐藏Employee
Salary
派生类中。那么下面的代码将不起作用;
Employee e = new Salary("John Adams", "Boston, MA", 2, 2400.00);
e.mailCheck();
由于mailCheck
hidden
Salary
基类中,因此e.mailCheck
将调用基类实现而不是派生类实现。
为了使用派生类实现,您有两个选项:
第一个选项:
您需要在声明为 Salary
类型的显式变量上显式调用mailCheck
,然后您需要像这样更改代码:
Employee e = new Salary("John Adams", "Boston, MA", 2, 2400.00);
((Salary)e).mailCheck();
// Or just like this:
Salary e = new Salary("John Adams", "Boston, MA", 2, 2400.00);
e.mailCheck();
第二种选择:
正如我已经说过的,重新实现基类方法并不意味着要将其重写到派生类中。你只是隐藏了这种方法。这就是为什么在将代码编译到 Visual Studio 中时,您不会收到错误,而是来自 VS 的警告,告诉您需要使用 new
关键字显式隐藏此重新实现的方法。new
关键字将告诉其他开发人员,将来会查看您的代码,知道您不会因为不了解自己在做什么而隐藏该方法。如果您不需要隐藏mailCheck
方法并且需要利用 OOP 多变性,则必须使用修饰符将mailCheck
方法标记到基virtual
然后必须将 override
修饰符添加到派生类方法中。Main
方法中的代码保持不变。
正如其他人已经说过的,Java不需要你明确地将重新实现的方法标记为重写,但是使用C#,你需要通过像你一样重新实现一种方法来明确说明你试图做什么,否则它只会隐藏它。