我知道我们不能在Java中覆盖静态方法,但有人可以解释下面的代码吗?
class A {
public static void a() {
System.out.println("A.a()");
}
}
class B extends A {
public static void a() {
System.out.println("B.a()");
}
}
我如何能够覆盖班级a()
中的方法B
?
答案 0 :(得分:54)
你没有在这里覆盖任何东西。要亲眼看看,请尝试在@Override
public static void a()
之前将B
注释放在类B
中,Java会抛出错误。
您刚刚在类a()
中定义了一个名为a()
的函数,该函数与类A
中的函数B.a()
截然不同(无关系)。
但是因为A.a()
与父类中的函数具有相同的名称,所以隐藏 B b = new B();
b.a() //prints B.a()
A a = (A)b;
a.a() //print A.a(). Uses the declared reference's class to find the method.
[由Eng指出。福阿德。在运行时,编译器使用声明的引用的实际类来确定要运行的方法。例如,
static
您无法在Java中覆盖静态方法。请记住{{1}}方法和字段与类关联,而不是与对象关联。 (虽然,在某些语言中,如Smalltalk,这是可能的)。
我在这里找到了一些好的答案:Why doesn't Java allow overriding of static methods?
答案 1 :(得分:9)
这称为hiding a method
,如Java教程Overriding and Hiding Methods中所述:
如果子类定义了具有与a相同签名的类方法 在超类中的类方法中,子类中的方法隐藏了 一个在超类中。
答案 2 :(得分:6)
static
方法未被继承,因此其B
方法的单独副本
static
与class
有关,而与Object
答案 3 :(得分:3)
您没有覆盖方法a()
,因为static
方法未被继承。如果你放了@Override
,你就会看到错误。
A.java:10: error: method does not override or implement a method from a supertype
@Override
^
1 error
但这并不能阻止你在两个类中定义具有相同签名的静态方法。
答案 4 :(得分:2)
此外,调用方法的选择取决于变量的声明的类型。
B b = null;
b.a(); // (1) prints B.a()
A a = new B();
a.a(); // (2) prints a.a()
在(1)中,如果系统关注b
的身份,则会抛出NPE
。在(2)处,a
的值被忽略。由于a
被声明为A
,因此会调用A.a()
。
答案 5 :(得分:1)
您的方法不是重写方法。你只是尝试在派生类的方法之前放置@Override注释。它会给你一个编译时错误。所以java不允许你覆盖静态方法。
答案 6 :(得分:1)
虽然接受了goblinjuice的回答,但我认为示例代码可以改进:
public class StaticTest {
public static void main(String[] args) {
A.print();
B.print();
System.out.println("-");
A a = new A();
B b = new B();
a.print();
b.print();
System.out.println("-");
A c = b;
c.print();
}
}
class A {
public static void print() {
System.out.println("A");
}
}
class B extends A {
public static void print() {
System.out.println("B");
}
}
产地:
A
B
-
A
B
-
A
如果B已覆盖print()
,则会在最后一行写入B.
答案 7 :(得分:0)
静态方法将通过其类名称调用,因此我们不需要创建类对象,我们只需使用类名称来调用它,因此我们无法覆盖静态
例如
class AClass{
public static void test(){
}
}
class BClass extends AClass{
public static void test(){}
}
class CClass extends BClass{
public static void main(String args[]){
AClass aclass=new AClass();
aclass.test(); // its wrong because static method is called
// by its class name it can't accept object
}
}
我们只是称之为
AClass.test();
表示无法覆盖静态类 如果它被覆盖,那么如何调整它。