例如,可以重写超类中的实例方法,但不能重写静态实例方法。

隐藏是父类有一个名为 Foo 的静态方法,子类也有一个名为 Foo 的静态方法。

另一个场景是父类有一个名为 Cat 的静态方法,子类有一个名为 Cat 的实例方法。(具有相同签名的静态和实例不能混用)。

public class Animal {


public static String getCat() { return "Cat"; }


public boolean isAnimal() { return true; }
}


public class Dog extends Animal {


// Method hiding
public static String getCat() { }


// Not method hiding
@Override
public boolean isAnimal() { return false; }
}
public class Animal {
public static void foo() {
System.out.println("Animal");
}
}


public class Cat extends Animal {
public static void foo() {  // hides Animal.foo()
System.out.println("Cat");
}
}

在这里,Cat.foo()被称为隐藏 Animal.foo()。隐藏不像重写那样工作,因为静态方法不是多态的。因此会发生以下情况:

Animal.foo(); // prints Animal
Cat.foo(); // prints Cat


Animal a = new Animal();
Animal b = new Cat();
Cat c = new Cat();
Animal d = null;


a.foo(); // should not be done. Prints Animal because the declared type of a is Animal
b.foo(); // should not be done. Prints Animal because the declared type of b is Animal
c.foo(); // should not be done. Prints Cat because the declared type of c is Cat
d.foo(); // should not be done. Prints Animal because the declared type of d is Animal

对实例而不是类调用静态方法是一种非常糟糕的做法,永远不应该这样做。

将其与实例方法进行比较,实例方法是多态的,因此会被重写。调用的方法取决于对象的具体运行时类型:

public class Animal {
public void foo() {
System.out.println("Animal");
}
}


public class Cat extends Animal {
public void foo() { // overrides Animal.foo()
System.out.println("Cat");
}
}

接下来会发生以下情况:

Animal a = new Animal();
Animal b = new Cat();
Cat c = new Cat();
Animal d = null;


a.foo(); // prints Animal
b.foo(); // prints Cat
c.foo(); // prints Cat
d.foo(): // throws NullPointerException

对于 覆盖,方法意味着每当对派生类的对象调用该方法时,将调用新的实现。

对于 藏起来来说,方法意味着在这个类的作用域内对这个名称的不限定调用(例如在它的任何方法的主体中,或者当用这个类的名称限定时)现在将调用一个完全不同的函数,需要从父类访问同名静态方法的限定

更多描述 Java 继承: 覆盖或隐藏方法

如果子类定义的类方法与超类中的类方法具有相同的签名,则子类中的方法将隐藏超类中的方法。

我相信隐藏的方法在静态上下文中。静态方法本身不会被重写,因为编译器在编译时本身执行的方法调用的解析。因此,如果在基类中定义一个静态方法,其签名与父类中的签名相同,那么子类中的方法将隐藏从父类继承的方法。

class Foo {
public static void method() {
System.out.println("in Foo");
}
}


class Bar extends Foo {
public static void method() {
System.out.println("in Bar");
}
}

首先,什么是方法隐藏?

方法隐藏意味着子类定义了与超类中的类方法具有相同签名的 类方法。在这种情况下,超类的方法被子类隐藏。它表示: 执行的方法的版本将由用于调用它的对象决定。事实上,它将由 用于调用方法的引用变量的类型决定。

什么是方法重写?

方法重写意味着子类定义了与超类中的实例方法具有相同签名和返回类型(包括协变类型)的 实例方法。在这种情况下,超类的方法被子类重写(替换)。它表示: 执行 < em > 的方法的版本将由用于调用它的对象确定它不会由用于调用该方法的引用变量的类型决定.

为什么不能重写静态方法?

因为,静态方法是基于调用它们的类来静态解析的(即在编译时) ,而不是像实例方法那样基于对象的运行时类型进行多态解析。

应该如何访问静态方法?

静态方法应该以静态的方式访问,即通过类本身的名称而不是使用实例。

下面是方法重写和隐藏的简短演示:

class Super
{
public static void foo(){System.out.println("I am foo in Super");}
public void bar(){System.out.println("I am bar in Super");}
}
class Child extends Super
{
public static void foo(){System.out.println("I am foo in Child");}//Hiding
public void bar(){System.out.println("I am bar in Child");}//Overriding
public static void main(String[] args)
{
Super sup = new Child();//Child object is reference by the variable of type Super
Child child = new Child();//Child object is referenced by the variable of type Child
sup.foo();//It will call the method of Super.
child.foo();//It will call the method of Child.


sup.bar();//It will call the method of Child.
child.bar();//It will call the method of Child again.
}
}

输出是

I am foo in Super
I am foo in Child
I am bar in Child
I am bar in Child

显然,如指定的,因为 foo是类方法,所以调用的 foo版本将由引用 Child对象的引用变量(即 Super 或 Child)的类型决定。如果它被 Super变量引用,则调用 Superfoo。如果它被 Child变量引用,那么 Childfoo被调用。
鉴于,
由于 bar是实例方法,因此调用的 bar版本完全由用于调用它的对象(即 Child)决定。不管通过哪个引用变量(SuperChild)调用它,将要调用的方法总是 Child

 class P
{
public static  void m1()
{
System.out.println("Parent");
}
}
class C extends P
{
public static void m1()
{
System.out.println("Child");
}
}
class Test{
public static void main(String args[])
{
Parent p=new Parent();//Parent
Child c=new Child();  //Child
Parent p=new Child();  //Parent
}
}


If the both parent and child class method are static the compiler is responsible for method resolution based on reference type


class Parent
{
public void m1()
{
System.out.println("Parent");
}}
class Child extends Parent
{
public void m1()
{
System.out.println("Child")
}
}
class Test
{
public static void main(String args[])
{
Parent p=new Parent(); //Parent
Child c=new Child();   //Child
Parent p=new Child();  //Child
}
}


If both method are not static  jvm is responsible for method resolution based on run time object

当超级/父类和子/子类包含包含相同参数和签名的相同静态方法时。父类中的方法将被子类中的方法隐藏。这就是所谓的方法隐藏。

例子: 1

class Demo{
public static void staticMethod() {
System.out.println("super class - staticMethod");
}
}
public class Sample extends Demo {


public static void main(String args[] ) {
Sample.staticMethod(); // super class - staticMethod
}
}

示例: 2-方法隐藏

class Demo{
public static void staticMethod() {
System.out.println("super class - staticMethod");
}
}
public class Sample extends Demo {
public static void staticMethod() {
System.out.println("sub class - staticMethod");
}
public static void main(String args[] ) {
Sample.staticMethod(); // sub class - staticMethod
}
}

首先,总是使用类名对静态方法进行分类。 如果函数是静态的,那么它是方法隐藏,而函数是非静态的,那么方法是重写的。