我试图了解受保护成员在类中的行为。我有一个TopClass
包含受保护整数的类pr
。
班级:
package com.test;
import com.test.anotherpackage.SubClass1;
import com.test.anotherpackage.SubClass2;
import com.test.anotherpackage.SubClass3;
public class TopClass {
protected int pr;
void action(TopClass t, SubClass1 s1, SubClass2 s2, SubClass3 s3) {
t.pr = 3;
s1.pr = 0;
s2.pr = 1;
s3.pr = 1;
}
}
还有另一个包com.test.anotherpackage
有 3 个类SubClass1
,SubClass2
和SubClass3
. 继承层次如下:
SubClass1 extends TopClass
SubClass2 extends SubClass1
SubClass3 extends SubClass2
子类1
package com.test.anotherpackage;
import com.test.TopClass;
public class SubClass1 extends TopClass {
void action(TopClass t, SubClass1 s1, SubClass2 s2, SubClass3 s3) {
t.pr = 0; // Error because not in same package.
s1.pr = 0; //(1)
s2.pr = 1; // Does not throw an Exception. Why? (2)
s3.pr = 1; // (3)
}
}
子类2
package com.test.anotherpackage;
import com.test.TopClass;
public class SubClass2 extends SubClass1 {
void action(TopClass t, SubClass1 s1, SubClass2 s2, SubClass3 s3) {
t.pr = 0; // Error because not in same package.
s1.pr = 0; // Throws Exception, why? (4)
s2.pr = 1; // (5)
s3.pr = 1; // Does not throw an Exception. Why?(6)
}
}
子类3
package com.test.anotherpackage;
import com.test.TopClass;
public class SubClass3 extends SubClass2 {
void action(TopClass t, SubClass1 s1, SubClass2 s2, SubClass3 s3) {
t.pr = 0;
s1.pr = 0; // Not Visible (7)
s2.pr = 1; // Not Visible (8)
s3.pr = 1; // (9)
}
}
在上面的代码中,(1)
, (2)
, (3)
,(5)
和(6)
完美(9)
地工作,没有任何可见性问题。但是(4)
, (7)
,(8)
存在可见性问题。
根据JLS§6.6.2.1,
令 C 为声明受保护成员的类。只有在 C 的子类 S 的主体内才允许访问。
此外,如果 Id 表示实例字段或实例方法,则:
如果通过限定名称 Q.Id 进行访问,其中 Q 是 ExpressionName,则当且仅当表达式 Q 的类型是 S 或 S 的子类时才允许访问。
如果通过字段访问表达式 E.Id(其中 E 是 Primary 表达式)或通过方法调用表达式 E.Id(. . .)(其中 E 是 Primary 表达式)进行访问,则当且仅如果 E 的类型是 S 或 S 的子类。
我想在这里理解的是为什么if the type of the expression Q is S or a subclass of S
会出现。是否有任何特定场景可以使此实施受益?任何相关的例子都将受到高度赞赏。我尝试在 SO 上查看它,但找不到可以解决我疑问的解释。