class SuperC implements Serializable {
int superValue;
public SuperC(int v) { superValue = v; }
public String toString() { return "superValue: " + superValue; }
}
class SubC extends SuperC {
int subValue;
public SubC(int sv, int v) { super(sv); subValue = v; }
public String toString() { return super.toString() + " sub: " + subValue; }
}
// 測試
SubC obj = new SubC(100, 200);
// 序列化 → 反序列化
// 輸出:superValue: 100 sub: 200
子類無需額外代碼即可完整序列化/反序列化父類欄位。
JavaDocs 規定兩個必要條件:
public abstract class SuperC { // 無 Serializable
int superValue;
public SuperC(int v) { superValue = v; } // 唯一建構子有參
// 缺少無參建構子
}
class SubC extends SuperC implements Serializable { ... }
// 編譯錯誤:Serializable cannot be resolved...
public abstract class SuperC {
int superValue;
public SuperC(int v) { superValue = v; }
public SuperC() {} // 關鍵:補上無參建構子
}
class SubC extends SuperC implements Serializable {
int subValue;
public SubC(int sv, int v) { super(sv); subValue = v; }
// 自定義序列化:先預設序列化自身,再手動寫入父類欄位
private void writeObject(ObjectOutputStream out) throws IOException {
out.defaultWriteObject();
out.writeInt(superValue);
}
// 自定義反序列化:先預設讀取自身,再手動讀取父類欄位
private void readObject(ObjectInputStream in) throws IOException, ClassNotFoundException {
in.defaultReadObject();
superValue = in.readInt();
}
}
defaultWriteObject()/defaultReadObject() 處理當前類別非 transient/non-static 欄位,父類欄位需手動讀寫並**順序一致**。
| 場景 | 處理方式 |
|---|---|
| 父類已實作 Serializable | 子類自動獲得序列化能力,無需額外代碼 |
| 父類未實作 Serializable | 1. 父類加無參建構子 2. 子類實作 writeObject/readObject 手動處理父類欄位 |