超类中的受保护方法在不同包中的子类中是不是可见? [复制]

Posted

技术标签:

【中文标题】超类中的受保护方法在不同包中的子类中是不是可见? [复制]【英文标题】:Is protected method in super class visible in sub class in a different package? [duplicate]超类中的受保护方法在不同包中的子类中是否可见? [复制] 【发布时间】:2018-05-27 18:19:58 【问题描述】:

这看起来很傻,但我真的很困惑。请看以下代码:

package com.one;
public class SuperClass 
    protected void fun() 
        System.out.println("base fun");
    

----
package com.two;
import com.one.SuperClass;
public class SubClass extends SuperClass
    public void foo() 
        SuperClass s = new SuperClass();
        s.fun(); // Error Msg: Change visibility of fun() to public 
    

我也从 oracle doc 和 here 中了解到,受保护的成员在另一个包的子类中也是可见的。所以 fun() 应该在包二的 SubClass 中可见。那为什么会报错呢?

我是否严重遗漏了一些非常明显的东西?

【问题讨论】:

该方法对SubClass 本身的实例可见。所以你可以拨打this.fun()。但是,如果您创建一个不同的实例并尝试调用它的方法,它将不允许,因为SubClass 的实例与SuperClass那个 实例无关。 “可见”并没有给你一个完整的画面。您可以在其自身上调用该方法,即this.fun() 或只是fun(),但是当您创建SuperClass 的新实例时,该方法是禁止使用的,因为SubClass 成为SuperClass 的“常规”客户端尽管也继承自它。 【参考方案1】:

Java Language Specification 说

对象的受保护成员或构造函数可以从包外部访问,只有负责实现该对象的代码才能在该包中对其进行声明。

这意味着如果您在原始类的包之外编写子类,则每个对象都可以在自身上调用超类的受保护方法,但不能在其他对象上调用。

在您的示例中,因为sthis 是不同的对象,所以您不能调用s.fun()。但是该对象将能够在其自身上调用fun 方法——使用this.fun() 或仅使用fun()

【讨论】:

【参考方案2】:

受保护的方法仅对内部的子类可见。如果您创建SuperClass 的新实例,则您正在从外部访问它。

【讨论】:

以上是关于超类中的受保护方法在不同包中的子类中是不是可见? [复制]的主要内容,如果未能解决你的问题,请参考以下文章

我们可以在父类的帮助下访问不同包中的受保护变量吗?

Java - 子类中的受保护变量是啥类型?

超类中的私有final可以被覆盖吗?

如何在子类中访问超类的“受保护的静态”变量,子类位于不同的包中......?

无法访问子类中的受保护方法[重复]

protect的简介