重新定义派生类中的静态成员。JAVA

重新定义派生类中的静态成员。JAVA,java,static,static-methods,Java,Static,Static Methods,所以我在读这本书,作者说“静态成员不涉及运行时多态性。您不能覆盖派生类中的静态成员,但可以重新定义它们。” 这是什么意思?你能给我举个例子吗 多谢各位 如果在子类中重新定义静态成员(方法或变量),则隐藏了超类的定义 public class Super { public static void methodA() { } } public class Sub extends Super { public static void methodA() {

所以我在读这本书,作者说“静态成员不涉及运行时多态性。您不能覆盖派生类中的静态成员,但可以重新定义它们。”

这是什么意思?你能给我举个例子吗


多谢各位

如果在子类中重新定义静态成员(方法或变量),则隐藏了超类的定义

public class Super
{
    public static void methodA()
    {

    }
}

public class Sub extends Super
{
    public static void methodA()
    {

    }
}
这里,静态
methodA
在子类中被重新定义,但它不会覆盖超类的
methodA


调用
Sub.methodA
将调用
Sub
methodA
。如果
Sub
没有
methodA
,调用
Sub.methodA
将调用
Super
methodA

如果在子类中重新定义静态成员(方法或变量),则隐藏了超类的定义

public class Super
{
    public static void methodA()
    {

    }
}

public class Sub extends Super
{
    public static void methodA()
    {

    }
}
这里,静态
methodA
在子类中被重新定义,但它不会覆盖超类的
methodA


调用
Sub.methodA
将调用
Sub
methodA
。如果
Sub
没有
methodA
,调用
Sub.methodA
会调用
Super
methodA

子类中的变量在超类中隐藏同名变量。

子类中的变量隐藏同名变量,在超类中。

如果在子类中重新定义静态方法,则称为方法隐藏。静态方法是在编译时而不是运行时解析的,您可以根据类调用它们,例如:

class A {
    public static void mymthod() {}
}

class B extends A {
    public static void mymthod() {}
}
你的电话是:

A a = new B();
a.mymthod();//resolved at compile time and associated with class A (compiler will warn although as static method doesnt necessarily need an object to call)

若您在子类中重新定义静态方法,它将被称为方法隐藏。静态方法是在编译时而不是运行时解析的,您可以根据类调用它们,例如:

class A {
    public static void mymthod() {}
}

class B extends A {
    public static void mymthod() {}
}
你的电话是:

A a = new B();
a.mymthod();//resolved at compile time and associated with class A (compiler will warn although as static method doesnt necessarily need an object to call)

你可以自己看看这个

class A {

    static int x = 1;
    int y = 1;

    int f() {
        return 1;
    }

    static int sf() {
        return 1;
    }
}

class B extends A {

    static int x = 2;
    int y = 2;

    int f() {
        return 2;
    }

    static int sf() {
        return 2;
    }

}

public class Test {

    /**
     * @param args the command line arguments
     */
    public static void main(String[] args) {
        A b = new B();
        System.out.println("A.x=" + ((A) b).x);
        System.out.println("B.x=" + b.x);
        System.out.println("A.y=" + ((A) b).y);
        System.out.println("B.y=" + b.y);
        System.out.println("A.f() = " + ((A) b).f());
        System.out.println("B.f() = " + b.f());
        System.out.println("A.sf() = " + ((A) b).sf());
        System.out.println("B.sf() = " + b.sf());

    }

}
它指出:

A.x=1 B.x=1 A.y=1 B.y=1 A.f()=2 B.f()=2 A.sf()=1 B.sf()=1

有人会期望B.sf打印为2,但不是

同样的一个会期望B.x和B.y打印为2,但也不是,因为字段也不是多态的,只是函数

我不确定这是否有多大的实用价值,一个人在犯了一个错误后肯定会知道这一点。
不过,在更糟糕的工作面试中很可能会问到这一点。

你可以自己看一看

class A {

    static int x = 1;
    int y = 1;

    int f() {
        return 1;
    }

    static int sf() {
        return 1;
    }
}

class B extends A {

    static int x = 2;
    int y = 2;

    int f() {
        return 2;
    }

    static int sf() {
        return 2;
    }

}

public class Test {

    /**
     * @param args the command line arguments
     */
    public static void main(String[] args) {
        A b = new B();
        System.out.println("A.x=" + ((A) b).x);
        System.out.println("B.x=" + b.x);
        System.out.println("A.y=" + ((A) b).y);
        System.out.println("B.y=" + b.y);
        System.out.println("A.f() = " + ((A) b).f());
        System.out.println("B.f() = " + b.f());
        System.out.println("A.sf() = " + ((A) b).sf());
        System.out.println("B.sf() = " + b.sf());

    }

}
它指出:

A.x=1 B.x=1 A.y=1 B.y=1 A.f()=2 B.f()=2 A.sf()=1 B.sf()=1

有人会期望B.sf打印为2,但不是

同样的一个会期望B.x和B.y打印为2,但也不是,因为字段也不是多态的,只是函数

我不确定这是否有多大的实用价值,一个人在犯了一个错误后肯定会知道这一点。
不过,在更糟糕的工作面试中可能会问这个问题。

我还是不太明白,对不起。你能给我举个例子吗?如果上面的方法不是静态的,那么它将被重写而不是重新定义,对吗?@taimeili123是的,如果方法不是静态的,子类中的方法将重写超类中的方法。我仍然不确定是否理解,抱歉。你能给我举个例子吗?如果上面的方法不是静态的,那么它将是重写而不是重定义的,对吗?@taimeili123是的,如果方法不是静态的,子类中的方法将重写超类中的方法。如果我错了,请原谅,重定义方法不是与重写方法相同吗?如果该方法不是静态的,那么它被认为是您给出的示例中的重写?是的,没错。但请参阅从对象调用的上下文,从直接类调用,运行时v/s编译时。请注意,该方法与类而不是对象关联。一旦定义了它的定义,就不能更改,因为它是静态的。如果我错了,请原谅我,但是重新定义一个方法不等于重写一个方法吗?如果该方法不是静态的,那么它被认为是您给出的示例中的重写?是的,没错。但请参阅从对象调用的上下文,从直接类调用,运行时v/s编译时。请注意,该方法与类而不是对象关联。一旦定义了它的定义,就不能更改,因为它是静态的。