對比 Java 1.4 與 C# 1.0 對基礎類型的處理,揭示 Java 違背「純面向物件」承諾的歷史包袱,與 C# 值類型的優雅統一。
Java 定義 8 種基礎類型(int、double、boolean 等),它們:
ObjecthashCode()、toString()ArrayList list = new ArrayList();
list.add(5); // 編譯失敗:int 非 Object
int i = (int)list.get(0); // 編譯失敗
int hash = 3.hashCode(); // 編譯失敗:基礎類型無成員
list.add(Integer.valueOf(5));
int i = ((Integer)list.get(0)).intValue();
int hash = Integer.valueOf(3).hashCode();
C# 無「基礎類型」概念,int、bool 等是 System.Int32、System.Boolean 等結構體(struct)的別名,統一繼承 ValueType → Object。
ArrayList list = new ArrayList();
list.Add(5); // 隱式裝箱
int i = (int)list[0]; // 隱式拆箱
int hash = 3.GetHashCode(); // 直接調用 Object 方法
| 特性 | 值類型 | 參考類型 |
|---|---|---|
| 賦值語義 | 整體複製 | 引用複製 |
| 記憶體分配 | 棧上 | 托管堆 |
| 生命週期 | 方法結束自動釋放 | GC 回收 |
| GC 壓力 | 無(除非裝箱) | 有 |
值類型適合高頻短命物件(並行計算臨時對象),避免 GC 成為瓶頸。裝箱/拆箱由 CLR 自動處理,無需手寫包裝類。
list.add(5); // 編譯器插入 Integer.valueOf(5)
int i = (Integer)list.get(0); // 編譯器插入 .intValue()
關鍵差異:3.hashCode() 仍編譯失敗。Java 編譯器不將基礎類型視為物件,僅在參數傳遞、賦值等特定語境插入轉換代碼。設計者堅持「基礎類型非物件」,自動裝箱只是「少寫代碼」,而非類型系統統一。
C# 值類型實現了「萬物皆物件」且保留高效能語義;Java 基礎類型造成類型系統割裂,自動裝箱掩蓋而非解決問題。這是語言設計哲學的根本分野。