A股上市公司传智教育(股票代码 003032)旗下技术交流社区北京昌平校区

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

© 郭晓晨 中级黑马   /  2013-12-19 12:54  /  1642 人查看  /  9 人回复  /   0 人收藏 转载请遵从CC协议 禁止商业使用本文

  1. class X
  2. {
  3.         Y b=new Y();
  4.         X()
  5.         {
  6.                 System.out.print("X");
  7.         }       
  8. }
  9. class Y
  10. {
  11.         Y()
  12.         {
  13.                 System.out.print("Y");
  14.         }
  15. }
  16. public class Z extends X
  17. {
  18.         Z()
  19.         {
  20.                 System.out.print("Z");
  21.         }
  22.         Y y=new Y();
  23.         public static void main(String[] args)
  24.         {
  25.                 new Z();
  26.         }
  27. }
复制代码


这段代码运行结果是YXYZ
但是我有点不理解,希望大神能给解释一下~

评分

参与人数 1技术分 +1 收起 理由
乔兵 + 1

查看全部评分

9 个回复

倒序浏览
类中实例变量的初始化在构造函数执行之前执行。
new Z()----->初始化实例变量y调用Y构造函数----->调用z构造函数--------->父类初始化-------->初始化实例变量y,调用构造函数--------调用父类构造函数--------->调用z的构造函数

评分

参与人数 1技术分 +1 收起 理由
乔兵 + 1

查看全部评分

回复 使用道具 举报

  1. class X
  2. {
  3.         Y b=new Y();
  4.         X()
  5.         {
  6.                 System.out.print("X");
  7.         }        
  8. }
  9. class Y
  10. {
  11.         Y()
  12.         {
  13.                 System.out.print("Y");
  14.         }
  15. }
  16. public class Z extends X
  17. {
  18.         
  19.         Z()
  20.         {
  21.                 System.out.println("Z");
  22.         }
  23.         {
  24.                     System.out.println("111111");
  25.             }
  26.         Y y=new Y();
  27.         {
  28.                     System.out.println("222222222222");
  29.             }
  30.         public static void main(String[] args)
  31.         {
  32.                 new Z();
  33.         }
  34. }
复制代码
运行结果为,
YX111111
Y222222222222
Z



开始代码运行时,首先是z类,由于z类继承与x,所以要首先加载X类,加载x类,首先是加载类的公共变量,也就是 Y b=new Y();,这一句是创建y类对象,所以执行new Y();时,就要加载Y类,进入Y类,加载Y类的构造函数,所以此时输出Y;加载完Y类后,又回到X类,继续加载X类的构造函数,从而输出X,然后就进入Z类,然后运行加载Z类里的 Y y=new Y();,此时又是创建Y类对象,所以又要加载Y类,进入Y类,加载构造函数,输出Y,Y类运行完后又回到Z类里,然后运行main函数,在main函数里有new Z();所以创建Z对象,加载Z类的构造函数,输出Z,这就是运行过程,你可以在一些地方加一些system.out.println();语句,使其输出一些字符观察运行顺序.

根据上面的代码,可见2楼的错了

评分

参与人数 1技术分 +1 收起 理由
乔兵 + 1

查看全部评分

回复 使用道具 举报
四五六七八 发表于 2013-12-19 13:31
类中实例变量的初始化在构造函数执行之前执行。
new Z()----->初始化实例变量y调用Y构造函数----->调用z构 ...

你理解貌似错了
回复 使用道具 举报
用new关键字创建一个类的对象时,先要找到这个类,查看它有没有父类,有的话(如本例中 Z extends X)就先给父类进行初始化(本例中即X类)在进行本类的初始化,按照给一个类进行初始化的顺序进行初始化,本题中只涉及实例变量及构造函数,实例变量的初始化在构造函数前执行。 所以先给父类进行初始化(先执行X中的  Y b=new Y()语句,再执行X的空参构造函数X())——再给本类进行初始化(先执行Z中的 Y y=new Y()语句,再执行Z的空参构造函数Z()

评分

参与人数 1技术分 +1 收起 理由
乔兵 + 1

查看全部评分

回复 使用道具 举报
刘松703 发表于 2013-12-19 13:49
运行结果为,
YX111111
Y222222222222

恩  确实是我搞错了
回复 使用道具 举报
taoge 中级黑马 2013-12-19 14:22:43
7#
楼上说明了原理,很清楚,用new关键字创建一个类的对象时,先要找到这个类,查看它有没有父类,有的话就先给父类进行初始化,)在进行本类的初始化,我原来还以为第二个X的输出是继承自X类的,查了下资料,原来构造函数不能被继承。涨知识了。
回复 使用道具 举报
刘松703 发表于 2013-12-19 13:49
运行结果为,
YX111111
Y222222222222

更正一点,程序是从主函数作为入口的哦!所以“然后运行main函数,在main函数里有new Z();所以创建Z对象,加载Z类的构造函数,输出Z”这样的说法是不对的,是开始运行代码时就是从main函数的newZ()语句执行的,这个时候因为Z继承了X,所以要先去初始化X
回复 使用道具 举报
张利星 发表于 2013-12-19 14:40
更正一点,程序是从主函数作为入口的哦!所以“然后运行main函数,在main函数里有new Z();所以创建Z对 ...

确实是表达错了哈哈
回复 使用道具 举报
谢谢各位的解答!
回复 使用道具 举报
您需要登录后才可以回帖 登录 | 加入黑马