2

这是我的超类:

class Superclass {

       int a=89;

       final  static void m( int p){
            System.out.println("Inside superclass");
       }   

       static void n(){
            system.out.print("superclass");
       }

}

这是我的子类::

 class Subclass extends Superclass {

        int a=90;

        static  void m( int p){
             System.out.println("Inside subclass");
        }

        static void n(){
             system.out.print("subclass");  
        }
  }

主类:

   class main {
        public  static void main(String[] args) {
            Subclass.m(89);
           new Subclass().n();
        }
   }

问题是我无法理解为什么 Javac 在静态方法中给了我覆盖错误。PS plzz 详细说明所有覆盖规则也适用于隐藏。喜欢

新方法定义必须具有相同的方法签名(即方法名称和参数)和相同的返回类型。覆盖方法中的参数是否应该是 final 由子类方法的签名决定,不包含参数的 final 修饰符,只包含它们的类型和顺序。

新的

方法定义不能缩小方法的可访问性,但可以加宽新的方法定义只能指定all或none,或者超类中被覆盖方法的throws子句中指定的异常类(包括其子类)的子集

我的错误是: 运行:

线程“主”java.lang.RuntimeException 中的异常:无法编译的源代码 - javaapplication3 中的 m(int)。子类无法覆盖 javaapplication3 中的 m(int)。超类覆盖的方法是静态的,最终在 javaapplication3.Subclass.m(JavaApplication3.java :18) 在 javaapplication3.min.main(JavaApplication3.java:25) Java 结果:1

我还想问一下,当方法被扩展超类的子类隐藏时,​​是否从类名调用静态成员来解析执行哪个版本的方法如果我创建匿名对象然后调用方法,那么编译器如何确定应该调用哪个版本的方法. 在上面的主类代码中,我输入:new Subclass().n();

即使我没有提供引用变量的类型,编译器如何知道应该调用方法的子类版本

4

2 回答 2

5

JLS 8.4.3.3

可以将方法声明为 final 以防止子类覆盖或隐藏它。

当从子类的实例调用时,与父类具有相同签名的静态方法会被隐藏。但是,您不能覆盖/隐藏最终方法。该关键字final将禁止隐藏该方法。所以它们不能被隐藏,尝试这样做会导致编译器错误。Javaranch上有一个很好的解释。

于 2013-07-07T11:23:07.883 回答
2

您在此处观察到的内容符合JLS 8.4.3.3规定:

尝试覆盖或隐藏最终方法是编译时错误。

您正在尝试覆盖final static void m子类中的方法,这是 Java 编译器不允许的。

于 2013-07-07T11:29:34.440 回答