面向对象编程
abstract关键字
1 什么是abstract关键字
1) abstract
关键字属于Java中的关键字,其能修饰的结构有:类和方法。
2) abstract
关键字的作用为限定被修饰的结构为抽象的结构,体现为不能够被直接使用。换句话说,能被abstract
修饰的结构一定能够被扩展为多个版本,而被abstract
修饰的结构作为抽象原始版本不能够被使用,只能通过使用其对应的扩展版本实现间接地对其使用。
这也能解释abstract
只能修饰类和方法:
- 类可以通过子类实现扩展,也就是说,子类就是父类的扩展版本。
- 方法可以通过重写实现扩展,这里隐含了一个信息,在应用上,被
abstract
修饰的方法一定处于有子类的类中。
2 abstract类
1) 类的使用,体现在类的实例化上,即创建类对应的对象。换句话说,类的直接使用就是创建类对应的直接对象。
2) abstract类
代表着该类不能实例化,换句话说,该类不存在直接属于该类的对象,这里也隐含了一个信息,在应用上,被abstract
修饰的类一定存在能够实例化对象的子类。
注意,虽然abstract
类不能实例化,但不代表没有构造器,因为其子类的构造器要调用,以加载父类成员。
抽象类的使用的前提:继承性。
3 abstract方法
1) 方法的直接使用,体现在对该方法的直接调用。
2) abstract
方法代表着该方法不能被直接调用,换句话说,对abstract方法
的调用只能是调用其重写版本,因此abstract方法
不存在方法体,其格式为:abstract methodName(args);
。
由于抽象方法不存在方法体,因此对抽象方法的重写,实际上更应该称为对抽象方法的实现。
由于一个方法一定能够被具有该方法的对象直接调用,因此具有abstract方法
的类限定为2种:
- 直接存在自己的
abstract方法
,即不是继承父类的abstract方法
,的类必须作为abstract类
。
如果不作为abstract类
就能具有abstract方法
的对象,对象就能直接调用abstract方法
。 - 自己本身不存在
abstract方法
,但继承了父类的abstract方法
,要么作为abstract类
,要么将继承的所有abstract方法
进行重写。
注意,虽然具有abstract方法
的abstract类
的子类能够通过super
来直接调用父类的结构,但是无法调用父类的abstract方法
,编译上就会报错。这是因为,子类用super调用父类的抽象方法相当于在继承了该抽象方法的基础上,又通过调用添加了一份该抽象方法到子类,这显然是不合理的操作。
另外,虽然abstract方法
无法被直接调用,但是其类内可以调用,但这并不影响,因为即使在类内调用该方法,具体的实现仍然是调用重写的该方法,因为abstract方法
存在于abstract类
中,因此不存在对该方法的直接调用。换句话说,类内调用抽象方法也不属于直接使用该抽象方法,只有对象调用方法时才属于方法被使用。
换句话说,abstract方法
不存在具有其abstract
内容的对象,只存在重写了该方法的对象,因此不管怎样,对其的使用都是使用其重写的版本。
4 abstract关键字的使用其他注意点
1) abstract
关键字不能修饰private方法
,可以从两方面理解:
private方法
是专门供类内部直接使用的方法,而abstract
限定方法不能被直接使用,二者是冲突的。private方法
不能被重写,而abstract方法
是只能使用其重写版本,二者是冲突的。
类内其他方法对private方法
的使用与对其他方法的使用是不同的,private方法
就是专门用于内部使用,因此内部使用时相当于使用了一个完全确定的方法,这也可以解释private方法
不能被重写。对于其他方法的使用,并不是相当于直接使用确定内容的方法,因为其他方法都可以被重写,内容是无法确定的,因此这就不属于直接使用该方法。
2) abstract
关键字不能修饰static方法
,也可以从两方面理解:
static方法
随类加载而加载,可以通过类.方法
的方式直接调用,而abstract方法
要求无法被直接使用,二者冲突。static方法
不能被重写。即使子、父类存在同名同参数的static方法
也无法构成重写。
这里本人认为本质上是因为static
结构是依赖于类的,(子、父类本质上仍是不同的类)只要是不同的类,其static方法
本质上就是不同的,而方法重写本质上是相同方法的两个版本。
3) abstract
关键字不能修饰final
类或final方法
。因为,final
限定不能改变,即不能有扩展,与abstract
完全对立。
4 abstract关键字的使用场景
- abstract方法:若一个方法随具体情况而定义功能,即无法在当前类中给一个笼统的功能定义。
- abstract类:直接存在
abstract方法
的类必须为abstract类
。