目录
抽象类只是在普通类的基础上,扩充了一些抽象方法
1.抽象方法
只声明而未实现的方法(没有方法体),所有抽象方法要求使用abstract来定义。
抽象方法所在的类也一定要使用abstract定义来表示抽象类。(有抽象方法的类一定是抽象类)
2.抽象类的使用原则
- 所有的抽象类必须有子类
- 抽象类的子类必须覆写抽象类的所有抽象方法(前提:子类不再是抽象类)
- 抽象类要想创建实例化对象,必须通过子类向上转型为其实例化。(抽象类无法创建实例化对象)
- abstract和final不能同时使用,final一定没有子类,abstract一定有子类。
- abstract和private也不能同时使用,private修饰后,子类看不见抽象类,无法覆写,与抽象类必须覆写矛盾。
代码示例:
public class AbstractClass{
public static void main(String[] args){
//抽象类无法创建实例化对象
//Person per = new Person();
//抽象类的实例化对象可以通过其子类实例化(多态)
Person per = new Student();
per.fun();
}
}
abstract class Person{
private String name;
public String getName(){
return name;
}
//抽象方法
public abstract void fun();
}
//子类继承抽象类,必须实现父类的抽象方法
//如果没有覆写父类的抽象方法,则必须使用abstract(编译通过,无法运行)
//子类覆写抽象类
class Student extends Person{
public void fun(){
System.out.println("子类继承父类");
}
}
/**
* 内部类、抽象类
* Author:qqy
*/
public class Test {
public static void main(String[] args) {
Person person=Person.getPersonObject();
System.out.println(person.getPersonInfo());
}
}
abstract class Person {
private String name;
public String getName() {
return name;
}
public Person(String name){
this.name=name;
}
abstract String getPersonInfo();
public static Person getPersonObject(){
//匿名内部类
return new Person("里斯"){
@Override
public String getPersonInfo() {
return "工人:"+this.getName();
}
};
//方法内部类
// class Worker extends Person{
// public Worker(String name){
// super(name);
// }
//
// @Override
// public String getPersonInfo() {
// return "工人:"+this.getName();
// }
// }
//
// return new Worker("张三");
}
}
3.对象实例化
对象的实例化操作实际上需要以下几个核心步骤:
a.进行类加载(类没有被使用->没有被加载->其静态块没有被使用,实例化一定要使用静态块)
b.进行类对象的空间开辟
c.进行类对象中的属性初始化(构造方法)
4.抽象类的相关规定
1.抽象类允许提供构造方法,并且子类也照样遵循对象实例化流程,先调用父类构造方法,而后调用子类构造方法。
练习:
abstract class A{
public A(){ //3.调用父类构造
this.print() ; //4.调用被子类覆写的方法
}
public abstract void print(); //4->5
}
class B extends A{
private int num = 100; //进入构造方法后初始化 private int a
public B(int num) { //2.调用子类实例化对象
super() ; //3.隐含一行语句,实际要先调用父类构造
this.print();
this.num = num ; //7.为类中属性初始化 this.a
}
public void print() { //5.此时子类对象的属性还没有被初始化
System.out.println(this.num) ; //6.对应其数据类型的默认值 0 this.a
}
}
public class Test{
public static void main(String[] args) {
new B(30) ; //1.实例化子类对象 ->0 //0 100
new B(30).print(); // ->0 30 //0 100 30
}
}
2.抽象类中允许不定义任何的抽象方法,但是此时抽象类依然无法直接创建实例化对象
3.abstract(有子类)和final(不能有子类)不能同时使用,abstract和private也不能同时使用
4.内部抽象类
子类不关心内部抽象类的内部抽象方法,只需关心父类中的直接抽象方法,内部抽象方法可由子类的内部类覆写。外部抽象类不能用static修饰,但内部抽象类可以用static修饰。
代码示例:
/**
* 抽象内部类
* Author:qqy
*/
public class InnerAbstractClass{
public static void main(String[] args){
Student student=new Student();
Student.C c=student.new C();
Person.B b=student.new C();
Worker worker=new Worker();
Person.E e=new Worker();
}
}
abstract class Person{
public abstract void test1();
//抽象内部类
static abstract class B{
public abstract void test2();
}
//静态抽象内部类
static abstract class E{
public abstract void test3();
}
}
class Student extends Person{
public void test1(){}
class C extends B{
public void test2(){
}
}
}
class Worker extends Person.E{
public void test3() {
}
}