1、概述
我们知道,类用来模拟现实事物。一个类可以模拟一类事物,而某个类的一个实例化对象可以模拟某个属于该类的具体的事物。类中描绘了该类所有对象共同的特性,当一个类中给出的信息足够全面时,我们就可以实例化该类;比方说,在Dog类中定义了name,age,fur_color,sex等属性,以及habit,eat等行为时,我们就可以创建一个Dog类对象,来模拟某个具体的Dog,比如你家的宠物狗,或者是神犬小七等。但是,当一个类中给出的信息不够全面时,(比方说有无法确定的行为),它给出的信息不足以描绘出一个具体的对象,这时我们往往不会实例化该类,这种类就是抽象类。打个比方,对于Animal类,是,所有的动物都有吃喝的行为,定义eat方法可以描述动物“吃”这一行为,但是每种动物吃的都不一样,因此一个eat方法并不能准确描述吃什么,怎么吃。这时Animal给出的信息就不足够描述一个对象,我们就不能去实例化Animal类。
在Java中,我们通过在类前添加关键字abstract(抽象的)来定义抽象类。如下所示 :
public abstract class Animal {
//Animal类此时就是一个抽象类。
}
class Dog extends Animal {
//Dog类继承了Animal类,是Animal类的子类。
}
2 抽象类的定义
在Java中,使用 abstract 关键字来定义一个抽象类。抽象类可以包含抽象方法和非抽象方法。抽象方法没有方法体,只有方法签名,必须在子类中被实现。
public abstract class Animal {
// 抽象方法
public abstract void makeSound();
// 非抽象方法
public void eat() {
System.out.println("Animal is eating.");
}
}
3.抽象类特性
抽象类不可以直接new对象。
抽象方法不可以封装起来,也就是不可以用private修饰。
抽象方法不能被final和static修饰,因为抽象方法,一定要被子类重写。
抽象类必须被继承,且子类必须要重写抽象方法,否则子类也是一个抽象类,且子类必须被abstract修饰。
抽象类中可以没有抽象方法,但是有抽象方法的类只能是抽象类。
抽象类也可以有构造方法,供子类来初始化父类的成员变量。
抽象类的应用
抽象类不能直接实例化,必须通过子类来实现。子类继承抽象类后,必须实现所有抽象方法。
public class Dog extends Animal {
// 实现抽象方法
@Override
public void makeSound() {
System.out.println("Dog says: Woof!");
}
}
public class Cat extends Animal {
// 实现抽象方法
@Override
public void makeSound() {
System.out.println("Cat says: Meow!");
}
}
抽象类的好处
1.代码复用:抽象类可以定义一些通用的方法,这些方法可以在子类中被重用。
2.接口定义:抽象类可以作为接口的实现,提供一些默认的行为。
3.强制子类实现:抽象方法强制子类实现特定的行为,保证了代码的一致性。
4.设计灵活性:抽象类可以作为模板,子类可以根据需要实现具体的行为。
3.抽象类总结规定
抽象类不能被实例化(初学者很容易犯的错),如果被实例化,就会报错,编译无法通过。只有抽象类的非抽象子类可以创建对象。
抽象类中不一定包含抽象方法,但是有抽象方法的类必定是抽象类。
抽象类中的抽象方法只是声明,不包含方法体,就是不给出方法的具体实现也就是方法的具体功能。
构造方法,类方法(用 static 修饰的方法)不能声明为抽象方法。
抽象类的子类必须给出抽象类中的抽象方法的具体实现,除非该子类也是抽象类。
示例代码
下面是一个完整的示例,展示了如何使用抽象类
// 定义抽象类
public abstract class Vehicle {
// 抽象方法
public abstract void start();
// 非抽象方法
public void stop() {
System.out.println("Vehicle is stopping.");
}
}
// 实现抽象类
public class Car extends Vehicle {
// 实现抽象方法
@Override
public void start() {
System.out.println("Car is starting.");
}
}
public class Motorcycle extends Vehicle {
// 实现抽象方法
@Override
public void start() {
System.out.println("Motorcycle is starting.");
}
}
// 测试抽象类
public class TestAbstractClass {
public static void main(String[] args) {
Vehicle car = new Car();
Vehicle motorcycle = new Motorcycle();
car.start(); // 输出: Car is starting.
motorcycle.start(); // 输出: Motorcycle is starting.
car.stop(); // 输出: Vehicle is stopping.
motorcycle.stop(); // 输出: Vehicle is stopping.
}
}
结论
- 抽象类不能实例化对象,如果实例化某个对象,就会报错,编译无法通过。只有抽象类的非抽象子类可以创建对象。
- 抽象类中不一定包含抽象方法,但是有抽象方法的类必定是抽象类。
- 抽象类中的抽象方法只是声明,不包含方法体,就是不给出方法的具体实现功能。
- 构造方法、类方法(用 static 修饰的方法)不能声明为抽象方法。
- 抽象类的子类必须给出抽象类中的抽象方法的具体实现,除非该子类也是抽象类。