java保护的构造函数和可访问性
如果一个类的子类在不同的包中,为什么我们不能用受保护的构造函数实例化它呢?如果可以访问受保护的变量和方法,为什么同样的规则不适用于受保护的构造函数
pack1:
package pack1;
public class A {
private int a;
protected int b;
public int c;
protected A() {
a = 10;
b = 20;
c = 30;
}
}
pack2:
package pack2;
import pack1.A;
class B extends A {
public void test() {
A obj = new A(); // gives compilation error; why?
//System.out.println("print private not possible :" + a);
System.out.println("print protected possible :" + b);
System.out.println("print public possible :" + c);
}
}
class C {
public static void main(String args[]) {
A a = new A(); // gives compilation error; why?
B b = new B();
b.test();
}
}
# 1 楼答案
只有当另一个包中的子类扩展了包含受保护变量和方法的类时,才能访问受保护变量和方法。 您可以访问子类b中的变量“b”,因为您扩展了类A。您将无法访问类C中的变量“b”,因为它没有扩展类A
访问子类中受保护构造函数的唯一方法是使用父类引用变量和子类对象
# 2 楼答案
我同意之前的海报,不知道为什么要这样做(在扩展类中以这种方式实例化父对象),但你甚至可以这样做:
# 3 楼答案
根据Java规范(https://docs.oracle.com/javase/specs/jls/se8/html/jls-6.html#jls-6.6.2.2)
在您的情况下,通过调用
super()
从B
访问受保护的A
构造函数将是合法的。然而,使用new
进行访问是不合法的# 4 楼答案
JLS 6.6.7回答了您的问题。子类只访问其父类的受保护成员,如果它涉及其父类的实现。因此,如果父构造函数受保护且位于不同的包中,则不能在子类中实例化父对象
# 5 楼答案
为什么类中需要
A obj=new A();
,而类b的对象本身就是class A
在c类中,它给出了错误,因为你正在访问A类的受保护属性,它是构造函数
在这种情况下,要获取类A的对象,必须在类A中使用此函数