现在的位置: 首页 > 综合 > 正文

java继承中,成员变量的覆盖

2013年09月17日 ⁄ 综合 ⁄ 共 1327字 ⁄ 字号 评论关闭

其实Java继承中,成员变量(包括静态变量,实例变量,常量)没有覆盖(override)一说,应该叫隐藏(hidden)。override只针对方法来说的。

 

当成员变量为private时,其他类不能直接访问到,只能通过非private方法

访问,因此直接按照分析方法的思路分析,如该方法是否有覆盖,该方法是否是静态方法。

 

当成员变量为static时,即静态变量,在类加载过程中就分配了内存,因此只与访问的变量类型有关。

class Super {

   static String v = "Super";

}

class Sub extends Super {

   static String v = "Sub";

   public static void main(String[] args) {

      Sub sub = new Sub();

      System.out.println(sub.v);  // 变量sub属于Sub类型,因此输出Sub

 

      Super sooper = new Super();

      System.out.println(sooper.v);  // 变量sooper属于Super类型,因此输出Super

 

      Super sb = new Sub();

      System.out.println(sb.v);  // 这里虽然new了一个Sub对象,但使用Super类型的变量sb指向它,(可以认为把Sub对象强转为了Super类型),因此输出的应该是Super

}

 

 

当成员变量为非private时(缺省,protected,public),只与访问的变量类型有关。


把上例中成员变量v的static变为public:

class Super {

   public String v = "Super";

}

class Sub extends Super {

   public String v = "Sub";

   public static void main(String[] args) {

      Super sb = new Sub();

      System.out.println(sb.v);  // 这里也是输出Super

}

这里如果要追问一步:为什么成员变量为public时,也只与访问的变量类型有关?

用“子类的同名变量只是隐藏(hidden)了父类的同名变量”来回答觉得只是从形式上回答了。

 

Super sb = new Sub() 这里有个隐式强制转换,显式写就是:
Super sb = (Super)new Sub();

 

因此问题转到强制转换:

System.out.println(((Super)new Sub()).v);

1. 强制转换怎么个转法,能把明明属于子类对象的实例变量v的值转为父类对象的Super?

2. 强制转换怎么处理重写方法?

 

(知其然不知其所以然)待...

2010.10.26

当调用子类构造函数构建子类对象的时候,必然会先调用父类的构造函数,即构建一个父类对象(怎么得到这个对象?),因此父类的成员(变量和方法)也会被构建。
如果存在同名,内存中将会同时存在父类的同名成员和子类的同名成员。由于Java的多态性只针对方法来说的,成员变量不存在多态,因此成员变量只与访问的变量类型有关,而方法的调用遵从多态的规则。

 

 

抱歉!评论已关闭.