Java 受保护访问修饰符
我有以下两段代码:Java 受保护访问修饰符,java,variables,protected,Java,Variables,Protected,我有以下两段代码: /** * */ 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.p
/**
*
*/
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);
}
}
通过上面的代码文件,我试图理解受保护访问修饰符的用途。在文件MyUtility中,我试图引用MyThread类的变量b。但它给了我以下错误:
Exception in thread "main" java.lang.Error: Unresolved compilation problem:
The field MyThread.b is not visibilty.
我关心的是变量b应该可以从子类访问,因为我已经扩展了Mythread。但它给了我编译时错误。另外,当我在超类中将此变量声明为静态时,我可以直接访问它。那么,当我尝试通过实例访问时,我做错了什么?您无法从实例访问受保护的属性。只能在继承类中访问它们。在这一行-
MyThread th1 = new MyThread (); int d = th1 . b ;
实际上,您正试图从实例
th1
访问受保护的属性。方法main不是MyThread的显式部分-如果要实现另一个函数,例如prtintB(),则可以使用带“.”运算符的直接访问。要从main访问它,您必须编写一个getter函数。来自great book,解释了对受保护范围的误解:
但是对于包外的子类来说,拥有
访问超类(父)成员?这意味着子类继承了
成员。然而,这并不意味着
包外部的子类可以使用引用访问成员
指向超类的实例。换句话说,受保护=
遗产Protected并不意味着子类可以处理
保护超类成员,就好像它是公共的一样。那么如果
包外部的子类获取对超类的引用(通过,
例如,在
子类的代码),子类不能在
访问受保护成员的超类引用。到
在包外部的子类中,受保护的成员也可以是
当子类使用对的引用时,默认值(甚至是私有的)
超类子类只能通过
继承。
因此,在您的情况下,您尝试使用引用来访问父类包外部的受保护成员:
MyThread th1 = new MyThread();
int d =th1.b; //b cannot be reached !
Java语言规范第6.6.2.1节将告诉您真相: 如果访问是通过字段访问表达式
E.Id
,其中E
是主表达式,或通过方法调用表达式E.Id(…)
,其中E
是主表达式,则当且仅当E
的类型是S
或S
的子类时,才允许访问
这里的
MyThread
是C
,MyUtility
是S
,b是Id
。因此,在MyUtility实例中,您不能使用引用实例pfMyThread
来访问其b
OP实际上试图从实例th1
访问受保护的属性:谢谢,我明白了您的意思。我将两种不同的可见性混合在一起。例如,一个用于继承,另一个用于继承。