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

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

© 王晓新 中级黑马   /  2012-6-15 23:12  /  1633 人查看  /  6 人回复  /   0 人收藏 转载请遵从CC协议 禁止商业使用本文

本帖最后由 王晓新 于 2012-6-15 23:46 编辑
  1. abstract class  Employee
  2. {
  3.         private String name;
  4.         private String id;
  5.         private double pay;
  6.         Employee(){}          [color=Red]//这条注释掉就会出现错误[/color]
  7.         Employee(String name,String id,double pay)
  8.         {
  9.                 this.name=name;
  10.                 this.id=id;
  11.                 this.pay=pay;
  12.         }
  13.         public abstract void work();
  14. }
  15. class Manager extends Employee //经理类
  16. {
  17.         private int bonus;
  18.         Manager(){}
  19.         Manager(String name,String id,double pay,int bonnus)
  20.         {
  21.                 super(name,id,pay);
  22.                 this.bonus=bonus;
  23.         }
  24.         public void work()
  25.         {
  26.                 System.out.println("Manager work");
  27.         }
  28. }
  29. class Pro extends Employee  //普通员工类
  30. {
  31.         Pro(){}
  32.         Pro(String name,String id,double pay)
  33.         {
  34.                 super(name,id,pay);
  35.         }
  36.         public void work()
  37.         {
  38.                 System.out.println("Pro work");
  39.         }
  40. }
  41. class AbstractTest
  42. {
  43.         public static void main(String[] args)
  44.         {
  45.                 new Manager().work();
  46.                 Pro p=new Pro();
  47.                 p.work();
  48.         }
  49. }
复制代码
我不理解为什么当抽象类里的无参构造函数去掉之后就会出错,难道在子类中定义的无参构造函数不会初始化对象么?还是说子类的属性(除了bonus)都是从父类继承的,所以必须继承父类的无参构造函数来初始化对象?

评分

参与人数 1技术分 +1 收起 理由
黄奕豪 + 1 赞一个!

查看全部评分

6 个回复

正序浏览
胡卿 中级黑马 2012-6-16 00:45:55
7#
  1. abstract class  Employee
  2. {
  3.         private String name;
  4.         private String id;
  5.         private double pay;
  6.         Employee(){}          [color=Red]//这条注释掉就会出现错误[/color]
  7.         Employee(String name,String id,double pay)
  8.         {
  9.                 this.name=name;
  10.                 this.id=id;
  11.                 this.pay=pay;
  12.         }
  13.         public abstract void work();
  14. }
  15. class Manager extends Employee //经理类
  16. {
  17.         //super();  这里省略了这条语句,子类初始化时默认调用父类中空参数构造函数,如果你改成super(String name,String id,double pay),那么就没问题了
  18.         private int bonus;
  19.         Manager(){}
  20.         Manager(String name,String id,double pay,int bonnus)
  21.         {
  22.                 super(name,id,pay);
  23.                 this.bonus=bonus;
  24.         }
  25.         public void work()
  26.         {
  27.                 System.out.println("Manager work");
  28.         }
  29. }
  30. class Pro extends Employee  //普通员工类
  31. {
  32.         Pro(){}
  33.         Pro(String name,String id,double pay)
  34.         {
  35.                 super(name,id,pay);
  36.         }
  37.         public void work()
  38.         {
  39.                 System.out.println("Pro work");
  40.         }
  41. }
  42. class AbstractTest
  43. {
  44.         public static void main(String[] args)
  45.         {
  46.                 new Manager().work();
  47.                 Pro p=new Pro();
  48.                 p.work();
  49.         }
  50. }
复制代码
回复 使用道具 举报
子类构造器调用父类构造器分如下几种情况:
1.子类构造器执行体的第一行使用super显示调用父类构造器,系统将根据super调用里传入的实参列表调用父类对应的构造器
2.子类构造器执行体的第一行代码使用this显示调用本类中重载的构造器,系统将根据this调用里传入的实参列表调用本类另一个构造器,执行本类中另一个构造器时即会调用父类的构造器
3.子类构造器执行体中既没有super调用,也没有this调用,系统将会在执行子类构造器之前隐式调用父类无参数的构造器,所以如果注释掉了父类的无参数构造器,肯定会报错

点评

Mark  发表于 2012-6-15 23:49
回复 使用道具 举报
哎呀,多谢楼上几位哥们的提醒,把这么关键的地方忘了。。谢谢
回复 使用道具 举报
在创建子类对象的时候,会先创建父类对象,这个过程是由子类构造方法中调用父类构造方法实现的,如果你没在子类构造方法的第一句调用父类构造方法,那么系统默认你调用了父类无参的构造方法。
但是你父类你不写构造方法,系统会默认给你加一个无参构造方法,但是你写了有参构造方法,系统就不会给你加无参构造方法,而此时子类要创建对象,找不到父类无参的构造方法,所以出错,这个跟抽象类是没关系的!

点评

说的 恰到好处!  发表于 2012-6-16 01:23

评分

参与人数 1技术分 +1 收起 理由
黄奕豪 + 1 “会先创建父类对象”,这个只是用了父类的.

查看全部评分

回复 使用道具 举报
当有super调用和this调用的情况:
1. 子类构造器的执行体的第一行代码使用super显示调用父类构造器,系统将根据super调用里传入的参数列表来确定调用父类的哪个构造器;
2. 子类构造器执行体的第一行代码使用this显示调用本类中重载的构造器,系统将根据this调用里传入的实参列表来确定本类的另一个构造器(执行本类的另一个构造器时即进入第一种情况)

评分

参与人数 1技术分 +1 收起 理由
黄奕豪 + 1 赞一个!

查看全部评分

回复 使用道具 举报
只要在程序中创建Java对象,系统总是先调用最顶层父类构造器,然后依次向下调用所有父类的初始化操作,最终执行本类的初始化操作返回本类的实例。
当子类构造器执行体中既没有super调用,也没有this调用,系统将会在执行子类构造器之前,隐式调用父类无参数的构造器。
而当你注释Employee(){} ,系统将找不到父类的无参数的构造器,因此报错。
回复 使用道具 举报
您需要登录后才可以回帖 登录 | 加入黑马