天天看點

Java入門姿勢【面向對象程式設計10】抽象類和接口

本次課程我們來主要講解一下抽象類以及接口,本期知識點在Java基礎學習中非常重要,尤其是接口在今後的程式設計生涯中,這些知識點将會一直陪伴你,是以沒有在這方面學習精通的同學記得要抓緊時間複習呀。

final關鍵字,想必很多人都不陌生,在使用匿名内部類的時候可能會經常用到final關鍵字。另外,Java中的String類就是一個final類。

修飾變量: 被他修飾的變量不可改變。一旦賦了初值,就不能被重新指派。

final int MAX_SPEED = 120;

修飾方法:該方法不可被子類重寫。但是可以被重載!

final void study(){}

修飾類: 修飾的類不能被繼承。比如:Math、String、System等。

final class A {}

了解以上使用“final關鍵字”,模拟實作Math類:

再次提醒注意:

注意:final不能修飾構造方法

final修飾基本資料類型,值隻能指派一次,後續不能再指派

final修飾引用資料類型,final Dog dog = new Dog("亞亞");,不能變化的引用變量的值,可以變化的是對象的屬性

示例練習:final關鍵字修飾引用變量

·抽象方法

使用abstract修飾的方法,沒有方法體,隻有聲明。定義的是一種“規範”,就是告訴子類必須要給抽象方法提供具體的實作。

·抽象類

使用abstract修飾的類。通過abstract方法定義規範,然後要求子類必須定義具體實作。通過抽象類,我們就可以做到嚴格限制子類的設計,使子類之間更加通用。

問題1:

Animal an = new Animal();沒有一種動物,名稱是Animal,是以Animal不能被執行個體化

解決:抽象類

問題2:

子類必須重寫父類的某個方法,否則出現編譯錯誤

解決:抽象方法

抽象類和抽象方法-代碼示例:

抽象類主要要點:

1.有抽象方法的類隻能定義成抽象類

2.抽象類不能執行個體化,即不能用new來執行個體化抽象類。

3.抽象類必須有構造方法,建立子類對象的時候使用

4.一個抽象類至少0個抽象方法,至多(所有的方法都是抽象方法)個抽象方法

5.子類必須重寫父類的抽象方法,不重寫就提示編譯錯誤;或者子類也定義為抽象類

6.override 重寫 implements 實作

父類的方法是抽象的,需要子類實作;父類的方法不是抽象的,子類可以重寫

接口就是規範,定義的是一組規則,展現了現實世界中“如果你是…則必須能…”的思想。如果你是天使,則必須能飛。如果你是汽車,則必須能跑。

接口的本質是契約,就像我們人間的法律一樣。制定好後大家都遵守。

接口的聲明格式:

定義接口的詳細說明:

通路修飾符:隻能是public或預設。

接口名:和類名采用相同命名機制。

extends:接口可以多繼承。

常量:接口中的屬性隻能是常量,總是:public static final 修飾。不寫也是。

方法:接口中的方法隻能是:public abstract。 省略的話,也是public abstract。

接口需要注意的點:

子類通過implements來實作接口中的規範。

接口不能建立執行個體,但是可用于聲明引用變量類型。

一個類實作了接口,必須實作接口中所有的方法,并且這些方法隻能是public的。

JDK1.8(不含8)之前,接口中隻能包含靜态常量、抽象方法,不能有普通屬性、構造方法、普通方法。

JDK1.8(含8)後,接口中包含普通的靜态方法、預設方法。

需求:飛機、鳥、超人,飛彈參加飛行表演。

思路1:定義一個父類Flyable,讓飛機、鳥、超人,飛彈都繼承該類。不可以,因為繼承表達的是is-a的關系,而飛機、鳥、超人不是一種事物,

思路2:使用接口,定義一個接口Flyable,讓飛機、鳥、超人,飛彈都實作該接口。接口表達是has-a的關系

代碼示例:定義Flyable 接口:

代碼示例:實作Flyable 接口:

示例:測試Flyable 接口:

總結1:接口的組成

接口和數組、類、抽象類是同一個層次的概念

成員變量:接口中所有的變量都使用public static final修飾,都是全局靜态常量

成員方法: 接口中所有的方法都使用public abstract修飾,都是全局抽象方法

構造方法:接口不能new,也沒有構造方法

接口做方法的形參,實參可以該接口的所有實作類

總結2:接口和多繼承

C++ 多繼承

好處 :可以從多個父類繼承更多的功能

缺點:不安全 有兩個父類Father1,Father2,都有一個方法giveMoney(),子類如果重寫了,沒有問題,如果子類沒有重寫,調用giveMoney()是誰的

Java 單繼承

好處:安全

缺點:功能受限

解決方案:既安全,功能又強大,采用接口。接口變相的使Java實作了C++的多繼承,又沒有C++多繼承的不安全性

public class Bird extends Animal implements Flyable,Sleepable

必須先extends 再implements

圖書類、學生類、新聞類、商品類等是不同的類,可是卻都需要有比較的功能,怎麼辦?共同的父類不可以,可以定義一個比較接口Comparable,其中定義一個實作比較的方法compareTo(Object obj)。讓各個類實作該接口即可。Java中就是這麼來實作的,下面就來模拟實作一下Comparable接口吧。

【示例】定義Comparable接口:

【示例】實作Comparable接口:

【示例】測試Comparable接口:

JDK7及其之前:

接口的變量都是public final static 全局靜态常量,無變化

接口中都是抽象abstract方法,不能有static方法(因為abstract和static、final、private不能共存)

JDK1.8及其之後:

接口中可以添加非抽象方法(static),實作類不能重寫,隻能通過接口名調用。

如果子類中定義了相同名字的靜态方法,那就是完全不同的方法了,直接從屬于子類。可以通過子類名直接調用

接口中可以添加非抽象方法(default),實作類可以重寫,隻能通過對象名調用

實作類可以直接使用default方法,可以重寫default方法,但是必須去掉default。(default隻能接口中使用)

上級接口中default方法的調用:MyInterface.super.method2()

提供非抽象方法的目的

為了解決實作該接口的子類代碼重複的問題

為了既有的成千上萬的Java類庫的類增加新功能,且不必對這些類重新進行設計。比如隻需在Collection接口中增加default Stream<E> stream(),相應的Set和List接口以及它們的子類都包含此的方法,不必為每個子類都重新copy這個方法。

【代碼示例】JDK8的接口新特征:

為什麼需要面向接口程式設計? 軟體設計中最難處理的就是需求的複雜變化,需求的變化更多的展現在具體實作上。我們的程式設計如果圍繞具體實作來展開就會陷入”複雜變化”的汪洋大海中,軟體也就不能最終實作。我們必須圍繞某種穩定的東西開展,才能以靜制動,實作規範的高品質的項目。

接口就是規範,就是項目中最穩定的核心! 面向接口程式設計可以讓我們把握住真正核心的東西,使實作複雜多變的需求成為可能。

通過面向接口程式設計,而不是面向實作類程式設計,可以大大降低程式子產品間的耦合性,提高整個系統的可擴充性和和可維護性。

面向接口程式設計的概念比接口本身的概念要大得多。設計階段相對比較困難,在你沒有寫實作時就要想好接口,接口一變就亂套了,是以設計要比實作難!

接口文法本身非常簡單,但是如何真正使用?這才是大學問。我們需要後面在項目中反複使用,大家才能體會到。

學到此處,能了解基本概念,熟悉基本文法,就已經是非常棒的咯。 請繼續努力!再請工作後,閑餘時間再看看上面這段話,相信你會有更深的體會。

Java入門姿勢【面向對象程式設計10】抽象類和接口
Java入門姿勢【面向對象程式設計10】抽象類和接口