博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Java访问子类对象的实例变量
阅读量:6245 次
发布时间:2019-06-22

本文共 4613 字,大约阅读时间需要 15 分钟。

对于Java这种语言来说,一般来说,子类可以调用父类中的非private变量,但在一些特殊情况下,

Java语言可以通过父类调用子类的变量

具体的还是请按下面的例子吧!

package com.yonyou.test;/** * 测试类 * @author 小浩 * @创建日期 2015-3-2 */class Base{	// 定义了一个名为i的实例变量	private int i = 2;	public Base()	{		this.display(); //注意这里面的this代表当前正在运行的对象,即Derived对象	}	public void display()	{		System.out.println(i);	}}// 继承Base的Derived子类class Derived extends Base{	// 定义了一个名为i的实例变量	private int i = 22;	// 构造器,将实例变量i初始化为222	public Derived()	{		i = 222;              //②	}	public void display()	{		System.out.println(i);	}}public class Test{	public static void main(String[] args)	{		// 创建Derived的构造器创建实例		new Derived();       //①	}}

  最后的结果是多少呢?没错就是0,是不是很意外,这里你需要明白。

public Base() { this.display(); //注意这里面的this代表当前正在运行的对象,即Derived对象 }

  这里面的this指的是当前正在运行的那个对象,那么当前运行的对象是谁?没错,就是Derived对象。

     为了确定是Derived,我们可以看下面的代码:

    

public Base()	{ 		System.out.println(this.i); //新增加的变量 其值为2		this.display(); //注意这里面的this代表当前正在运行的对象,即Derived对象		System.out.println(this.getClass());	}     //最后结果为:      //    2     //    0     //    class com.yonyou.test.Derived

 

  

 

     但是现在的问题又出现了如果修改上面的代码加入System.out.println(this.i)

     如下面的例子:

public Base()	{ 		System.out.println(this.i); //新增加的变量 其值为2		this.display(); //注意这里面的this代表当前正在运行的对象,即Derived对象	}

  既然这俩this的指的是Derived对象,那为什么其值不是0,而是父类Base对象里面对应变量

     的值2呢?

     这里涉及到了编译类型和运行时类型相关的内容。当变量的编译类型和运行时类型不同的话,通过该对象访问其所引用对象的实例变量的时候

     表现出该实例变量所声明时的类型决定。因为

      System.out.println(this.i); //新增加的变量 其值为2

     这里的this访问的变量,所以其值为声明它的对象Base的值,即2

     但通过通过此实例变量调用它所对应的实例方法的时候,该方法的行为将由它实际所引用的对象来决定。

     因为

     this.display(); //注意这里面的this代表当前正在运行的对象,即Derived对象

     这里的this的实际引用它的对象为Derived,所以其i值为0.

     根据java创建对象时初始化对象的时机(),我们知道这时Derived中的变量i还没有初始化,

     所以最后的结果为:0

     最后提示一下如果是静态方法的话,仅仅序声明它的类型相关,与其它的没有任何关系哦...

    下面是对比的例子:

    1 静态方法,仅仅与其声明的类型有关

     

package com.yonyou.test;/** * 测试类 * @author 小浩 * @创建日期 2015-3-20 */public class Test { 	public static void main(String[] args) {               Base b=new Base();               Base  c=new Inherit();               b.a();               b.b();               c.a();               c.b();    }	}	class Base{        static void a( ){System.out.println("A");  }                 void b( ){System.out.println("B"); }} class  Inherit extends Base{          static void a( ){System.out.println("C");  }                  void b( ){System.out.println("D"); }        }

 最后的结果为:A,B,A,D  

2.非静态方法正常,与其真正所引用的类型相关

     

package com.yonyou.test;/** * 测试类 * @author 小浩 * @创建日期 2015-3-20 */public class Test { 	public static void main(String[] args) {               Base b=new Base();               Base  c=new Inherit();               b.a();               b.b();               c.a();               c.b();    }	}	class Base{         void a( ){System.out.println("A");  }                 void b( ){System.out.println("B"); }} class  Inherit extends Base{           void a( ){System.out.println("C");  }                  void b( ){System.out.println("D"); }        }

  结果为:A,B,C,D

   

     上面的话有一些绕,请务必多读几遍,反复揣摩,这样你会更上一层楼。

     如果实在不懂也可以发送邮件至:12612455595@qq.com

     如果你确实理解了的话,请通过下面的例子测试一下:

    

package com.yonyou.test;/** * 测试类 * @author 小浩 * @创建日期 2015-3-2 */class Animal{	// desc实例变量保存对象toString方法的返回值	private String desc;	public Animal()	{		// 调用getDesc()方法初始化desc实例变量		this.desc = getDesc();            //②	}	public String getDesc()	{		return "Animal";	}	public String toString()	{		return desc;	}}public class Wolf extends Animal{	// 定义name、weight两个实例变量	private String name;	private double weight;	public Wolf(String name , double weight)	{		// 为name、weight两个实例变量赋值		this.name = name;                 //③		this.weight = weight;	}	// 重写父类的getDesc()方法	@Override	public String getDesc()	{		return "Wolf[name=" + name + " , weight="			+ weight + "]";	}	public static void main(String[] args)	{		System.out.println(new Wolf("灰太狼" , 32.3)); //①	}}

 

     提示:最后的结果为:

     Wolf[name=null , weight=0.0]

    测试例子2:

   

class Base{	int count = 2;	public void display()	{		System.out.println(this.count);	}}class Derived extends Base{	int count = 20;	@Override	public void display()	{		System.out.println(this.count);	}}public class FieldAndMethodTest{	public static void main(String[] args)	{		// 声明、创建一个Base对象		Base b = new Base();             //①		// 直接访问count实例变量和通过display访问count实例变量		System.out.println(b.count);		b.display();		// 声明、并创建一个Derived对象		Derived d = new Derived();       //②		// 直接访问count实例变量和通过display访问count实例变量		System.out.println(d.count);		d.display();		// 声明一个Base变量,并将Derived对象赋给该变量		Base bd = new Derived();         //③		// 直接访问count实例变量和通过display访问count实例变量		System.out.println(bd.count);		bd.display();		// 让d2b变量指向原d变量所指向的Dervied对象		Base d2b = d;                    //④		// 访问d2b所指对象的count实例变量		System.out.println(d2b.count);	}}

 

  运行结果为:

    

2220202202

  

 

     好吧,今天就先到这里吧、、、

转载地址:http://fqoia.baihongyu.com/

你可能感兴趣的文章
Elasticsearch5.2.0部署过程的坑
查看>>
go build 不同系统下的可执行文件
查看>>
浏览器版本信息判断整理
查看>>
【我的Android进阶之旅】解决Android Studio 运行gradle命令时报错: 错误: 编码GBK的不可映射字符...
查看>>
windows 下解决 Time_Wait 和 CLOSE_WAIT 方法
查看>>
SOUI Editor使用教程
查看>>
PHP字符串的替换(preg_replace)
查看>>
责任链模式的具体应用
查看>>
Nginx安装
查看>>
Aix下查看内存命令
查看>>
[Android]JsonObject解析
查看>>
最好用的软件快速开发平台-全部源码-3800/套
查看>>
移动端fixed后 横竖屏切换时上部或下部出现空隙问题
查看>>
Django ORM 操作 必知必会13条 单表查询
查看>>
selenium 安装与 chromedriver安装
查看>>
ethereumjs/ethereumjs-vm-1-简介
查看>>
go标准库的学习-fmt
查看>>
iOS开发UI篇—推荐两个好用的Xcode插件(提供下载链接)
查看>>
Java集合框架中的快速失败(fail—fast)机制
查看>>
特殊的上下文选择符
查看>>