1. 程式人生 > 其它 >Day03=面向物件基礎+進階

Day03=面向物件基礎+進階

技術標籤:Java基礎學習筆記

面向物件 Object Oriented

面試常考點:面向物件的特性?
面向物件是一個建模的思路,關注具備功能(函式方法)的物件,把有共同屬性和功能的物件視為一個類,將這些共同的屬性和功能/行為抽象出來,並且封裝進類class裡實現。如果後面需要做一些工作(需求)的時候,就建立物件(new),讓物件來做這些事情(呼叫方法)。這就很像一個工具。
物件是很厲害的,封裝了一堆你想要實現的功能。你不需要知道這些功能怎麼實現,只要建立物件並且調物件的對應的方法就行。
(spring中的控制反轉就是將建立物件的這個控制權限也交給spring了,只需要提供配置檔案就可以讓spring的容器生成Bean物件。工廠模式


還可能考到的:c++和java的區別?這裡面向過程/面向物件也是一個區別,還可以答指標,記憶體回收等。
面向過程需要關注很繁瑣的過程。而面向物件不用關注實現的具體細節,而是關注統籌架構(巨集觀整體)的問題。

面向物件常考面試題-三大特徵

  • 封裝:所有內容對外部不可見(外部只能調方法)
  • 繼承:將其他的功能繼承並發展
  • 多型:方法的過載本身就是多型性的體現 (相同方法名,不同引數)
    還有可能問到的擴充套件問題:多型在類載入的哪個階段?

類與物件

類是共性,是總結起來的總和特徵,物件是個性,是個體。
根據類製造物件。類裡面有抽象出來的共同屬性和方法,定義物件的操作。類必須通過物件才可以使用。

類的定義

public
class Demo{ //成員屬性 //成員方法 }

一個.java檔案裡可以存在N個類,但只能存在一個public修飾的類。這表示編譯單元有單一的公共介面。.java的名稱必須與public修飾的類完全一致。(但是內部類可以有public)

記憶體區域

答題要點:

  • 可訪問特性:棧中元素執行緒私有,其他棧不可訪問。
  • 資料結構特性:先進先出。
  • 存取速度:比堆快,僅次於PC暫存器
  • (存取快的原因)棧記憶體空間的建立與釋放:棧指標的移動->確定大小和範圍->對資料儲存出現限制->只儲存少部分資料(大部分資料儲存於堆記憶體中)
  • 資料儲存的限制:資料大小與生存期都已確定(如何確定?),缺乏靈活性。
  • 儲存內容:基本資料型別的資料+引用資料型別的引用

  • 儲存內容:類的物件(通過new建立的那些,new是告訴JVM去開闢新的一塊堆記憶體空間去建立新的物件)
  • 儲存空間:建立的時候不用管
  • 記憶體釋放:當不存在該物件的引用時,視為垃圾,垃圾回收器回收。

方法區

建立物件時,類的資訊+方法就被載入到了方法區裡。

記憶體建立過程

  1. Book b1 存入棧記憶體,賦值null
  2. = new Book();放入堆記憶體,得到記憶體地址比如0x1234,則佔記憶體中修改b1的null為引用(0x1234)。
  3. 先從棧記憶體找b1,得到記憶體地址(引用)0x1234,然後到堆記憶體的相應位置上找物件。
  4. 複製物件,新增b2進棧記憶體,在棧記憶體中是相同的引用。
  5. 釋放:先從棧記憶體以後進先出的形式釋放,這樣堆記憶體中的物件就沒有引用,就會被GC。

方法過載

如果一個方法只是定義來運算int型別的,但是此時需要運算double?
類中定義的方法允許過載(相同的方法名稱),限制有:

  1. 方法名稱相同
  2. 引數列表長度||型別||順序
    如果只是返回值不一樣,不構成方法過載。

匿名

沒有引用名。在棧記憶體中有名字,裡面儲存引用,指向堆記憶體。
如果是匿名物件,只能用一次,因為下一次就找不到堆記憶體的位置了。
直接建立物件並呼叫方法 new Math().sum();

封裝

設定物件的時候會遇見邏輯錯誤,如果直接操作物件,不能避免。封裝的意義就是保護或防止資料無意破壞。就是不讓類以外的程式直接訪問和修改成員屬性。如何實現?

  • 隱藏物件的屬性和實現細節(將屬性私有)
  • 僅對外公開方法,並且還控制方法的訪問級別
    即,將成員屬性修飾為private這樣別的程式就不能直接操作物件的屬性啦。
    在賦值時傳入的引數不符合要求(if判斷),列印錯誤。

this關鍵字

調屬性調方法都行。

Person(){
	this("xxx",1);//this呼叫了另一個構造方法
}
Person(String s, int a){
}
  • this在一個構造方法中,呼叫另一個構造方法時,必須編寫在第一行,構建完物件之後才能對物件進行操作。(super也有這個特性,原因?)

快捷建立getter和setter

  • 放在宣告的屬性後面可以建立(source)
  • shift+alt+s也可以

如果有很多員工需要修改同一屬性至同一值region

  • 讓region指向一個static變數“北京”
    原:private String region

靜態屬性:
private static String region此時儲存於方法區中,含有自己的記憶體地址,所有的員工物件持有region的記憶體地址。
類載入方面的知識點:

  • static修飾的方法或者變數不需要像之前依賴物件.方法()的形式去訪問。它是在類被載入之後(靜態成員在類載入時載入並初始化然後儲存在方法區)就可以通過類名去訪問了。靜止不動的。不會因為物件多次建立而隨之在記憶體中多次建立(物件公用)。
  • 靜態不能訪問非靜態,但是非靜態可以訪問靜態。原因:靜態資源可被呼叫的時機早於非靜態資源。

Emp.region = "";可以直接通過類名訪問
用一個static int count並在每個構造方法裡++,則可以列印建立次數。

  • main方法的static不需要建立物件來呼叫,可以直接用。a的main中直接b.say();

  • 包=類+介面
  • 不同包中類名可以相同,加上包名以避免衝突
  • 包限定訪問許可權,有許可權的才能訪問某個包中的類
  • package name;
  • 所有單詞字母小寫,單詞之間.隔開,一般為com.公司名.專案名.模組名....(是域名,一般不太會重複)(實際上資料夾分層了)
    導包時也可以寫類的全名稱:
    java.util.Scanner input = new java.util.Scanner(System.in);
    同一個包中的其他類使用時也不用導包

許可權修飾符

  • public都可以訪問
  • protected其他包不能訪問
  • default只有本類和包能訪問,子類都不能
  • private只有本類中能訪問,包內其他類都不能

程式碼塊

  • 構造程式碼塊,(直接寫在class下的{},不是方法)類中的成員程式碼塊,每次物件建立時執行,且在構造方法之前執行。
  • 靜態程式碼塊,類中使用static修飾的成員程式碼塊。在類載入時執行。程式啟動到關閉只執行一次
  • 同步程式碼塊。多執行緒。
  • 執行順序:靜態程式碼塊->構造程式碼塊->構造方法

main方法詳解

  • public 可以被所有操作呼叫
  • static 可以通過類名呼叫
  • void 沒有返回值
  • main JVM只認這個為程式入口
  • String[] args 字串陣列,接受引數(控制檯引數,多個)
    輸出看看:
    其實這個陣列長度為0,沒有輸出
    這些引數是在執行java命令時傳遞的。
    java Demo1 haha haha hehe
    就可以有輸出了

問題總結

  1. 棧中的資料大小與生存期是如何確定的?
  2. 如果複製物件b2=b1,改變b2的屬性,那麼最後打印出來的b1的屬性也會更改,因為指向相同的引用
  3. super必須放第一行的原因?