Appearance
Abstract Class
Due to the existence of polymorphism, each subclass can override the methods of the parent class, for example:
java
class Person {
public void run() { … }
}
class Student extends Person {
@Override
public void run() { … }
}
class Teacher extends Person {
@Override
public void run() { … }
}
Both Student
and Teacher
derived from the Person
class can override run()
method.
If the run()
method of the parent class Person
has no practical meaning, can the execution statement of the method be removed?
java
class Person {
public void run(); // Compile Error!
}
The answer is no, it will cause compilation errors, because when defining a method, the statement of the method must be implemented.
Can I remove run()
method of the parent class?
The answer is still no, because if you remove the run()
method of the parent class, you lose the polymorphic feature. For example, runTwice()
will not compile:
java
public void runTwice(Person p) {
p.run(); // Person does not have a run() method, which will cause compilation errors.
p.run();
}
If the method of the parent class itself does not need to implement any function, but is just to define the method signature so that the subclass can override it, then the method of the parent class can be declared as an abstract method:
java
class Person {
public abstract void run();
}
Declaring a method as abstract
means that it is an abstract method and does not implement any method statement itself. Because this abstract method itself cannot be executed, the Person
class cannot be instantiated. The compiler will tell us that the Person
class cannot be compiled because it contains abstract methods.
The Person
class itself must be declared abstract
in order to compile it correctly:
java
abstract class Person {
public abstract void run();
}
If a class
defines a method but does not have specific execution code, the method is an abstract method, and the abstract method is modified with abstract
.
Because abstract methods cannot be executed, this class must also be declared as an abstract class.
A class modified with abstract
is an abstract class. We cannot instantiate an abstract class:
java
Person p = new Person(); // Compilation error
What is the use of an abstract class that cannot be instantiated?
Because the abstract class itself is designed to be inherited only, the abstract class can force the subclass to implement the abstract method it defines, otherwise the compilation will report an error. Therefore, abstract methods are actually equivalent to defining "specifications".
For example, the Person
class defines the abstract method run()
. Then, when implementing the subclass Student
, the run()
method must be overridden:
java
public class Main {
public static void main(String[] args) {
Person p = new Student();
p.run();
}
}
abstract class Person {
public abstract void run();
}
class Student extends Person {
@Override
public void run() {
System.out.println("Student.run");
}
}
Programming towards abstraction
When we define the abstract class Person
and the specific Student
and Teacher
subclasses, we can reference instances of the specific subclasses through the abstract Person
type:
java
Person s = new Student();
Person t = new Teacher();
The advantage of this kind of reference to the abstract class is that when we call its method, we don't care about the specific subtype of Person
type variable:
java
// Does not care about the specific subtype of the Person variable:
s.run();
t.run();
The same code, if the reference is to a new subclass, we still don't care about the specific type:
java
Person e = new Employee();
e.run();
This approach of referencing high-level types as much as possible and avoiding referencing actual subtypes is called abstraction-oriented programming.
The essence of abstraction-oriented programming is:
The upper code only defines specifications (for example: abstract class Person
); Business logic can be implemented without subclassing (normal compilation); Specific business logic is implemented by different subclasses, and the caller does not care.
Summary
The method defined by abstract
is an abstract method, which only has a definition but no implementation. Abstract methods define interface specifications that subclasses must implement;
A class that defines an abstract method must be defined as an abstract class, and subclasses that inherit from an abstract class must implement the abstract method;
If the abstract method is not implemented, the subclass is still an abstract class;
Abstraction-oriented programming makes the caller only care about the definition of abstract methods and not the specific implementation of subclasses.