0

我试图了解受保护成员在类中的行为。我有一个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 个类SubClass1SubClass2SubClass3. 继承层次如下:

  1. SubClass1 extends TopClass
  2. SubClass2 extends SubClass1
  3. 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 上查看它,但找不到可以解决我疑问的解释。

4

1 回答 1

0

您正在讨论的表达式也是对代码中您的问题负责的表达式:

if the type of the expression Q is S or a subclass of S

(2)因为表达式的类型s2是子类SubClass1
(4)因为表达式的类型s1不是子类SubClass2
(5)因为表达式的类型s3是子类SubClass2

然而,我不知道

此实施可能有益的任何特定场景

任何一个。

于 2013-07-07T21:52:49.573 回答