日期:2014-05-20  浏览次数:20701 次

请教protected问题
//B.java
import pa.*;
class B extends A{
public static void main(String args[]){
A a = new A();

a.i = 2;
a.print();
a.StPrint();

(new A()).StPrint();
}
}

//A.java
package pa;
public class A{
protected int i = 1;
protected void print(){
System.out.println("print");
}
protected static void StPrint(){
System.out.println("StPrint");
}
}
B和A不在同一个包中,B继承A,为什么B可以访问A的StPrint方法,不能访问A的print方法。


------解决方案--------------------
public static void main(String args[]) {
A a = new A();
a.i = 2; // i 是 A 的 protected field, 不在同一个package内无法访问
a.print();// print 是 A 的 protected method, 不在同一个package内无法访问

a.StPrint(); // 因为StPrint 是static Method , static method 调用
// 不需要通过对象的实例,跟写成 A.StPrint() 是一样的效果
// 也就是说在B的main函数里面调用了父类的一个 protect method, (new A()).StPrint(); //同上

B b = new B();
b.i = 2; // 是 B 的field 所以能访问
b.print(); // B继承的方法,可以访问
b.StPrint(); // B 继承的方法,可以访问
}
这里面要注意的就是: a.i, a.print() 的a是A的实例,
而 a.StPrint()方法貌似跟a.print()类似,实际上确跟A.stPrint()等价,
而它的protected属性表明了它可以被子类直接调用。
------解决方案--------------------
为了避免混绕, 建议避免将静态函数写成a.stprint(), 如果你使用Eclipse,你会发现会有一个警告:
The static method stprint() from type A should be accesed in a static way
------解决方案--------------------
我觉得还是那句话,子类是不能继承父类构造方法的

所以你在B当中实例化A的时候,肯定要将A的构造方法声明为public的了,现在是protected说明符,在不同包内是无法访问的

构造方法跟普通方法,变量是不一样的,继承的时候也是如此
------解决方案--------------------
子类为什么不能继承父类的构造方法?
我的想法如下:
1. 从A本身来说, public A(){}, protectedA(){}, private A(){} 都没有任何问题
所不同的是 new A() ;这个方法的调用范围不一样而已。
2. B extends A . 那么 B(){}; 等价于B(){super());
也就是说,B的构造方法首先得调用父类的某一个构造函数,然后才能干点其它的什么,
所以,当A(){}声明为public或者protected的时候没有任何问题,
只有当A(){} 声明为private的时候会报错,因为此时,B不能调用任何A的构造函数