1. 程式人生 > >Java之路:抽象類

Java之路:抽象類

抽象類

在Java中可以建立一種類專門用來做父類,這種類稱為“抽象類”。抽象類實際上也是一個類,只是與之前的普通類相比,內部新增了抽象方法。

1、抽象方法

抽象方法是隻宣告而未實現的方法。

例:

void f();	// 只有宣告,沒有實現。 

2、抽象類的定義與使用

(1)抽象類和抽象方法都必須用abstract關鍵字來修飾;

(2)抽象類不能直接例項化,也就是不能直接用new關鍵字去產生物件;

(3)抽象類定義時抽象方法只需宣告,而不需實現;

(4)含有抽象方法的類必須被宣告為抽象類,抽象類的子類必須覆寫所有的抽象方法後才能被例項化,否則這個子類還是個抽象類。

(5)抽象類可以定義普通方法,普通方法可以有方法體。

例:

public abstract class Book {
	private String bookName = "《Java程式設計思想》";	// 定義屬性:書名
	public void printName() {	// 定義普通方法:列印書名
		System.out.println(bookName);
	}
	public abstract void f();	// 定義一個抽象方法
	public static void main(String[] args) {
		Book b = new Book
(); // 錯誤,抽象類無法例項化物件 } }

【結果】
在這裡插入圖片描述

其實,抽象類也就是比普通類多了一些抽象方法而已。 如果說一個類的物件可以被例項化,那麼就表示這個物件可以呼叫類中的屬性和方法,但是抽象類中存在抽象方法,而抽象方法沒有方法體,沒有方法體的方法自然無法使用了。

(6)抽象類必須有子類,子類使用extends繼承抽象類,一個子類只能夠繼承一個抽象類子類(如果不是抽象類),則必須要全部覆寫抽象類中的全部抽象方法;如果想要例項化抽象類的物件,則可以使用子類進行物件的向上轉型來完成。

例:

abstract class Person     //定義一抽象類Person
{ String name; int age; String occupation; public abstract String talk();//宣告一個抽象方法talk() } class Student extends Person //Student類繼承自Person類 { public Student(String name,int age,String occupation) { this.name=name; this.age=age; this.occupation=occupation; } public String talk() //覆寫抽象方法talk() { return"學生——>姓名:"+this.name+",年齡:"+this.age+",職業:"+this.occupation+"!"; } } public class AbstractClassDemo { public static void main(String[] args) { Student s=new Student("張三",20,"學生"); //建立Student類物件 Person p = new Student("王五",22,"學生"); // 向上轉型為Person類 System.out.println(p.talk()); //呼叫被覆寫過的方法 System.out.println(s.talk()); //呼叫被覆寫過的方法 } }

【結果】
在這裡插入圖片描述

(7)抽象類中可以有構造方法。

與一般類相同,在抽象類中也可以擁有構造方法,但是這些構造方法必須在子類中被呼叫,並且子類例項化物件的時候依然滿足類繼承的關係,先預設呼叫父類的構造方法,而後再呼叫子類的構造方法,畢竟抽象類之中還是存在屬性的,只不過這個抽象方法無法直接被外部例項化物件的時候所使用。

abstract class Person     //定義一抽象類Person
{
	String name;
	int age;
	String occupation;
	public Person(String name, int age, String occupation) {	// 定義一構造方法
		this.name=name;
		this.age=age;
		this.occupation=occupation;
	}
	public abstract String talk();//宣告一個抽象方法talk()
}
class Student extends Person  //Student類繼承自Person類
{
	public Student(String name,int age,String occupation)
	{
		super(name, age, occupation);	// 子類必須先呼叫抽象類的構造方法
		this.name=name;
		this.age=age;
		this.occupation=occupation;
	}
	public String talk()    //覆寫抽象方法talk()
	{
		return"學生——>姓名:"+this.name+",年齡:"+this.age+",職業:"+this.occupation+"!";
	}
}
public class AbstractClassDemo
{
	public static void main(String[] args)
	{
		Student s=new Student("張三",20,"學生");  //建立Student類物件s
		Person p = new Student("王五",22,"學生");	// 向上轉型為Person類
		
		System.out.println(p.talk());              //呼叫被覆寫過的方法
		System.out.println(s.talk());              //呼叫被覆寫過的方法
	}
}

【結果】
在這裡插入圖片描述

綜上可知,抽象類也可以像普通類一樣,有構造方法、一般方法和屬性,更重要的是還可以有一些抽象方法,需要子類去實現,而且在抽象類中宣告構造方法後,在子類中必須明確呼叫

(8)抽象類不能夠用final定義。

使用final定義的類不能有子類,而抽象類使用的時候必須有子類,這是一個矛盾的問題,所以抽象類上不能出現final定義。

(9)在外部抽象類上無法使用static宣告,但是內部抽象類卻可以使用static定義,使用static定義的內部抽象類就表示一個外部類。

例:

abstract class Book {	// 外部抽象類無法用static宣告
	public abstract void print();	// 抽象方法
	
	static abstract class CD {	// 靜態內部抽象類,相當於一個外部類
		public abstract void get();	// 抽象方法
	}
}

class JavaCD extends Book.CD { // 繼承靜態內部抽象類
	@Override
	public void get() { // 重寫靜態內部抽象類的抽象方法
		System.out.println("Java學習!");
	}
}

public class StaticInnerAbstractClass {
	public static void main(String[] args) {
		Book.CD cd = new JavaCD();	// 例項化物件,向上轉型為父類CD
		cd.get();
	}
}

【結果】
在這裡插入圖片描述

(10)抽象類之中可以沒有抽象方法,但即便沒有抽象方法的抽象類也不能夠直接通過關鍵字new例項化。

例:

abstract class Book {	// 沒有抽象方法的抽象類
}

public class StaticInnerAbstractClass {
	public static void main(String[] args) {
		Book b = new Book();	// 錯誤,無法例項化
	}
}

【結果】
在這裡插入圖片描述