Java 为什么在这种情况下调用父类方法而不是子类?
我有一个父类a和它的子类B。它们都有Java 为什么在这种情况下调用父类方法而不是子类?,java,inheritance,Java,Inheritance,我有一个父类a和它的子类B。它们都有doSomething方法和不同类型的参数 甲级 package Inheritance; public class A { public void doSomething(Object str){ System.out.println("Base impl:"+str); } } B类 package Inheritance; public class B extends A{ public void doS
doSomething
方法和不同类型的参数
甲级
package Inheritance;
public class A {
public void doSomething(Object str){
System.out.println("Base impl:"+str);
}
}
B类
package Inheritance;
public class B extends A{
public void doSomething(String str){
System.out.println("Child impl:"+str);
}
public static void main(String[] args) {
A a = new B();
a.doSomething("override");
}
}
当我运行它时,我得到“Base impl:override”作为输出
a
指向B
的对象,他传递的参数是String
,所以当您使用类型a的引用时,它不应该调用B
的doSomething(String str)
方法吗?,您只能看到为类A定义的方法。因为B中的doSomething
不会覆盖A中的doSomething
(因为它有不同的签名),所以不会调用它
如果要使用类型B的引用,这两种方法都是可用的,并且会选择B的
doSomething
,因为它有一个更具体的参数(字符串与对象)。我想这不被认为是方法重写的情况,因为签名不完全相同。将字符串参数更改为B中的Object。在类A中,您已经声明了一个方法doSomething(objectobj)
。但是,在类B中,您声明了方法doSomething(String str)
,该方法的参数类型与类a中的不同。这意味着类B的doSomething
不会覆盖类a的doSomething
要获得所需的输出,请执行以下操作(我省略了获取更通用代码示例的主要方法):
正如@Eran所说
使用类型a的引用时,只能看到为类a定义的方法。由于B中的doSomething不会覆盖a中的doSomething(因为它具有不同的签名),因此不会调用它。
如果你想调用在B中定义的方法,你需要按如下方式转换它
((B)a).doSomething("override");
或者你必须隐式地使用B的实例你的意思是当我这样做时说:“A=新B();”a、 doSomething(“覆盖”);'第一个编译器将检查一个类的doSomething(String),但它不存在!然后发现A有doSomething(对象),因为doSomething(对象)在B类中没有被重写,所以调用父级的doSomething(对象)。我说的对吗?@praveshp是的
doSomething(Object)
是A中唯一匹配调用A.doSomething(“override”)
的方法,这意味着每当我执行“ParentClass obj=new ChildClass();”时若使用obj调用任何方法,编译器将首先在ParentClass中检查该方法,因为obj的类型为Parent。如果找到,它将检查ChildClass是否已重写相同的。“这就是流动吗?”PraveeshP差不多了。编译器将在ParentClass中找到最适合方法调用参数的方法。如果找不到,代码将无法编译。只有在运行时,JVM才会检查obj
实例的实际类型,并根据该调用检查ChildClass方法(如果它重写父类方法)。
((B)a).doSomething("override");