简体   繁体   English

受保护的访问修饰符

[英]Protected Access Modifier

I have the following two piece of code : 我有以下两段代码:

/**
 * 
 */
package com.akshu.multithreading;

/**
 * @author akshu
 *
 */
public class MyThread extends Thread {
    protected  int b;   

    private int a;
    @Override
    public void run() {

        super.run();

        System.out.println("int a:"+a);
    }

}



-----------


package com.akshu.utility;

import com.akshu.multithreading.MyThread;

public class MyUtility extends MyThread{

    public static void main(String args[])
    {
        MyThread th1 = new MyThread();
        int d =th1.b;  // line1
        System.out.println("int d"+d);
    }

}

with the above files of code i am trying to understand purpose of protected access modifier. 使用上面的代码文件,我试图了解受保护的访问修饰符的目的。 In the file MyUtility , I am trying to refer variable b of class MyThread.But its giving me below error: 在文件MyUtility中,我试图引用类MyThread.But的变量b,它给我下面的错误:

Exception in thread "main" java.lang.Error: Unresolved compilation problem: 
    The field MyThread.b is not visibilty.

My concern is variable b should be accessible from subclass as i have already extended the Mythread. 我担心的是变量b应该可以从子类访问,因为我已经扩展了Mythread。 But it is giving me compile time error. 但它给了我编译时错误。 Also when i declare this variable as static in my superclass i was able to access it directly .So what wrong i am doing when i am trying to access via instance? 此外,当我在我的超类中将此变量声明为静态时,我能够直接访问它。当我尝试通过实例访问时,我正在做什么错?

You can't access protected properties from an instance. 您无法从实例访问受保护的属性。 You can only access them in inheriting class. 您只能在继承的类中访问它们。 In this line- 在这一行 -

MyThread  th1  = new MyThread (); int  d  = th1 . b ;

you are actually trying to access a protected property from an instance th1 . 您实际上是尝试从实例th1访问受保护的属性。

The method main is not explicitly part of MyThread - if you would implement another function, eg prtintB(), you could use the direct access with the "." 方法main不是MyThread的明确部分 - 如果你要实现另一个函数,例如prtintB(),你可以使用“。”直接访问。 operator. 运营商。 To access it from main you have to write a getter function. 要从main访问它,你必须编写一个getter函数。

From Kathy Sierra's great book, explaining the misunderstanding of protected scope: 凯西塞拉的伟大着作,解释对protected范围的误解:

But what does it mean for a subclass-outside-the-package to have access to a superclass (parent) member? 但是,包的子类可以访问超类(父)成员是什么意思? It means the subclass inherits the member. 这意味着子类继承了成员。 It does not, however, mean the subclass-outside-the-package can access the member using a reference to an instance of the superclass. 但是,它并不意味着子类外包可以使用对超类实例的引用来访问该成员。 In other words, protected = inheritance. 换句话说,protected = inheritance。 Protected does not mean that the subclass can treat the protected superclass member as though it were public. 受保护并不意味着子类可以将受保护的超类成员视为公开成员。 So if the subclass-outside-the-package gets a reference to the superclass (by, for example, creating an instance of the superclass somewhere in the subclass' code), the subclass cannot use the dot operator on the superclass reference to access the protected member. 因此,如果子类 - 外包获得对超类的引用(例如,通过在子类'代码中的某处创建超类的实例),子类不能使用超类引用上的点运算符来访问受保护的成员。 To a subclass-outside-the-package, a protected member might as well be default (or even private), when the subclass is using a reference to the superclass. 对于包之外的子类,当子类使用对超类的引用时,受保护的成员也可能是默认成员(甚至是私有成员)。 The subclass can see the protected member only through inheritance. 子类只能通过继承来查看受保护的成员。

Thus, in your case, you try to use a reference to access a protected member outside parent's class package: 因此,在您的情况下,您尝试使用引用来访问父级类包之外的受保护成员:

MyThread th1 = new MyThread();
int d =th1.b;  //b cannot be reached !

Java lang specification section 6.6.2.1 will tell you the truth : Java lang规范第6.6.2.1节将告诉你实情:

If the access is by a field access expression E.Id , where E is a Primary expression, or by a method invocation expression E.Id(. . .) , where E is a Primary expression, then the access is permitted if and only if the type of E is S or a subclass of S . 如果通过字段访问表达式E.Id (其中E是主表达式)或通过方法调用表达式E.Id(. . .) (其中E是主表达式)进行访问,则仅当且仅当允许访问时,如果类型ES或的一个子类S

Here MyThread is C , MyUtility is S and b is Id . 这里MyThreadCMyUtilityS ,b是Id So in a MyUtility ionstance you cannot use a reference to an instance pf MyThread to access its b 因此,在MyUtility ionstance中,您不能使用对实例pf MyThread的引用来访问其b

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM