【问题标题】:Overriding protected methods in Java覆盖 Java 中的受保护方法
【发布时间】:2011-08-04 00:07:03
【问题描述】:

Test.java

package a;
import b.B;
public class Test {
    public static void main(String[] v) {
        new A().test();
        new B().test();
    }
}

A.java:

package a;
public class A {
    protected void test() { }
}

B.java:

package b;
public class B extends a.A {
    protected void test() { }
}

为什么new B().test() 会报错?这不会违反可见性规则吗?

B.test()Test 中是不可见的,因为它们位于不同的包中,但它拒绝调用可见的B 超类中的test()

如果能提供 JLS 相应部分的链接,我们将不胜感激。

【问题讨论】:

  • “给出错误” .. 你能说得更具体点吗?
  • @Kevin 他在问为什么他不能调用他可以访问超级方法的方法。
  • @Jeremy:它拒绝编译:“a/Test.java:10: test() has protected access in b.B”
  • @Kevin:阅读问题:“这不违反可见性规则吗?”
  • @Jeremy 错误(在这种情况下)相当明显:这是一个编译时错误,说 B().test()a.Test.main(String[]) 不可见。

标签: java methods overriding protected


【解决方案1】:

这里是 protected 关键字上的 JLS: JLS protected descriptionJLS protected example

基本上protected 修饰符意味着您可以访问给定类的子类中的字段/方法/ ... 1) 和 2) 从同一包中的类。

因为 2) new A().test() 有效。但是new B().test() 不起作用,因为B 类在不同的包中。

【讨论】:

    【解决方案2】:

    这不是继承在 Java 中的工作方式。

    如果一个方法被覆盖,而被覆盖的方法是不可见的,那么尝试调用它是一个编译时错误。

    您似乎期望 Java 会自动回退到超类中的方法,但事实并非如此。

    稍后我将尝试挖掘 JLS,以了解为什么不这样做......

    【讨论】:

      【解决方案3】:

      问题是在编译时你告诉 Java 你想访问一个类的受保护成员,而你没有这样的访问权限。

      如果你这样做了;

        A a = new B();
        a.test();
      

      然后它会工作并且被覆盖的方法将运行,因为在编译时Java会检查您是否可以访问A。在运行时,提供的对象具有适当的方法,因此B test() 方法会执行。动态绑定或后期绑定是关键。

      【讨论】:

        【解决方案4】:

        是的,覆盖受保护的方法是可能的。

        class A{
        protected void f(){
        SOP("A");
        }}
        class B extends A{
        protected void f(){
        SOP("B");
        }
        public static void main(String...args)
        {
        B b=new B();
        b.f();
        }
        }
        

        输出:B

        【讨论】:

          猜你喜欢
          • 2013-07-01
          • 1970-01-01
          • 2015-10-01
          • 1970-01-01
          • 2022-07-08
          • 1970-01-01
          • 2012-01-26
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多