一、继承的概念
——一种由已有的类创建新类的机制,是面向对象程序设计的基石之一
——通过继承,可以根据已有类来定义新类,新类拥有已有类的所有功能
——Java只支持类的单继承,每个子类只能有一个直接父类
——父类是所有子类的公共属性及方法的集合,子类则是父类的特殊化
继承机制可以提高程序的抽象程度,提高代码的可重用性
基类(base class)
——也称超类(superclass)
——是被直接或间接继承的类
派生类(derived-class)
——也称子类 (subclass)
——继承其他类而得到的类
——继承所有祖先的状态和行为
——派生类可以增加变量和方法
——派生类也可以覆盖(override)继承的方法
派生类产生的对象
——从外部来看,它应该包括
与基类相同的接口
可以具有更多的方法和数据成员
——其内包含着一个基类类型的子对象
二、属性的继承与隐藏
——子类中声明了与父类中相同的成员变量名,则从父类继承的变量将被隐藏
——子类拥有了两个相同名字的变量,一个继承自父类,另一个由自己声明
——当子类执行继承自父类的操作时,处理的是继承自父类的变量,而当子类执行它自己声明的方法时,所操作的就是它自己声明的变量
如何访问被隐藏的父类属性
——一、调用从父类继承的方法,则操作的是从父类继承的属性
——二、使用super.属性
子类不能继承父类中的静态属性,但可以对父类中的静态属性进行操作。子类不能继承父类的静态属性体现在通过子类的类名不能直接调用该静态属性。通过子类创建的实例以及在子类的方法中是可以对该静态属性进行操作的。子类在创建实例即对象时,内部包含着基类类型的一个子对象。
三、方法的继承与重写(覆盖)
——如果子类不需使用从父类继承来的方法的功能,则可以声明自己的同名方法,称为方法覆盖
——覆盖方法的方法名称,参数的个数及类型必须和被覆盖的方法一摸一样
——只需在方法名前面使用不同的类名或不同类的对象名即可区分覆盖方法和被覆盖方法
——覆盖方法的访问权限可以比被覆盖的宽松,但是不能更为严格
——覆盖方法抛出异常的类型范围不能超过被覆盖的方法。
——覆盖方法的返回值类型小于等于父类的返回类型
方法覆盖的应用场合
子类中实现与父类相同的功能,但采用不同的算法或公式
在名字相同的方法中,要做比父类更多的事情
在子类中需要取消从父类继承的方法
必须覆盖的方法
派生类必须覆盖基类中的抽象的方法,否则派生类自身也成为抽象类.
不能覆盖的方法
基类中声明为final的终结方法
基类中声明为static 的静态方法
调用被覆盖的方法
super.overriddenMethodName();
四、子类的构造方法
有继承时的构造方法遵循以下的原则
——子类不能从父类继承构造方法
——好的程序设计方法是在子类的构造方法中调用某一个父类构造方法,调用语句必须出现在子类构造方法的第一行,可使用super关键字
——如子类构造方法的声明中没有明确调用父类构造方法,则系统在执行子类的构造方法时会自动调用父类的默认构造方法(即无参的构造方法),所以以一个好的程序设计习惯就是在每个类中都编写一个无参的构造方法。否则当该类被继承时在子类中若没有明确调用父类的构造方法,系统会自动调用父类的默认构造方法,而父类却没有无参构造构造方法,编译会报错。
代码演示:
class Person
{
protected String name, phoneNumber, address;
public Person()
{
this("", "", "");
}
public Person(String aName, String aPhoneNumber, String anAddress)
{
name=aName;
phoneNumber=aPhoneNumber;
address=anAddress;
}
}
class Employee extends Person
{
protected int employeeNumber;
protected String workPhoneNumber;
public Employee(){
//此处隐含调用构造方法 Person()
}
}
说明:如果将Person类中的无参构造方法注释掉,Employee类的构造方法会报错,There is no default constructor available in ‘baoming.Person’;在Person中没有无参构造方法。所以在一个类中不管有参的构造方法有多少,有且最好有一个无参的构造方法,当然若你确定该类不会被继承或者你使用super关键字调用有参的构造方法,则不需要有。