讀<<Java解惑>>後的碎嘴子(第五章)

第五章--類問題

46.
public class Confusing {
   	private Confusing(Object o) {
		System.out.println("Object");
	}
	private Confusing(double[] dArray) {
		System.out.println("double array");
	}
	public static void main(String[] args) {
		new Confusing(null);
	}
}
會打印哪個呢?答案是double array,遠離了該死的各種數字二進制死循環和try塊,本章終於來點面向對象的東西了,這頭一條就很讓我開眼,重點在於當構造方法發生overload時選擇的規律是精確優先於抽象,即double數組類型是一個Object,而Object顯然不是一個double數組,當然了,如果在new中聲明瞭具體的類型如Object,那就不會發生這樣的現象了
總結:這個規律還是很少有人知道的,和<<effective java>>裏一樣,大師再一次提醒了慎用overload,但是普通方法還好,構造方法沒法起不同的名字,如參數太多,也可以考慮採用builder設計模式

47.代碼比較多,原因很簡單,本條重點在於說明static域不僅由本類實例共享,其子類實例也會共享同一個static域,不會因爲家族類總個數的變化而變化
總結:除了上面的原因,順便要學會分清has-a和is-a的區別,發揚組合優於繼承的光榮傳統

48.代碼還是比較多,原因還是很簡單,對於static方法,不存在override,也不存在晚編聯機制(運行時動態決定調用哪個方法,俗稱多態),而是用的早編聯機制(在編譯時就決定了調用哪個方法,根據引用類型來配對而不是多態裏的實現類型),這個例子在IDE裏顯示也會有警告,因爲static方法不需要由對象來引用
總結:Java裏並不是所有東西都是面向對象的,當然這也沒什麼不好

49.這條算是比較簡單的,涉及了類加載後static初始化的一些順序問題,儘管在現實中基本看不到這種不入流的singleton
總結:瞭解一個類加載時,各個元素的加載順序是每個人必知必會的事情

50.
String s = null;
System.out.println(s instanceof String);
說明instanceof操作符優先會排除null,不管它是何類型的引用
System.out.println(new Test() instanceof String);
編譯會失敗,引出instanceof另一個很直接的特徵:操作符左右要麼是同一類型,要麼是父子類關係
Test test = (Test) new Object();
編譯會成功,但是運行時會扔出熟悉的ClassCastException,和上面的例子形成了很有意思的對比,編譯器本條應該查到這個錯誤卻沒有,上一條應該理論上返回false但卻連編譯都不能通過
總結:非要說的話,就是編譯器畢竟是死的,其實instanceof還有不少讓人犯暈的特點,大師並沒有提到

51.基本和49條基本是一回事,涉及了構造方法的調用順序問題,這裏的問題在現實中很難犯,也很容易被察覺
總結:同49條

52.繼續順序的問題,涉及了static塊和static域的初始化順序問題
總結:static塊的執行(包括調用了其它的static方法)的整個過程都優先於static域值的初始化

53.本條是一個構造器的技巧用法,並沒有涉及到不容易理解的內在機制

54.沒什麼展示代碼和總結的必要了,本條是一個很簡單的提示

55.作爲本章的最後一條,並沒有什麼值得深刻記憶的地方
總結:從中引申出5.0中java.util.concurrent包的各主要併發類,需要深刻了解和理解
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章