承接系列首篇,本文詳細講解每具體類一表 策略的映射文件編寫規則,包括字段重複定義、關聯映射重複、以及初始化註冊細節。
COMPANIES — 公司表HOURLY_EMPLOYEES (HE) — 時薪員工表SALARIED_EMPLOYEES (SE) — 月薪員工表子表包含父類所有字段 (ID, NAME) + 自身字段 (RATE/SALARY) + 關聯外鍵 (COMPANY_ID)。
.hbm.xml<hibernate-mapping>
<class name="mypack.HourlyEmployee" table="HOURLY_EMPLOYEES">
<id name="id" column="ID"><generator class="increment"/></id>
<property name="name" column="NAME"/> <!-- 繼承字段重複定義 -->
<property name="rate" column="RATE" type="double"/> <!-- 自身字段 -->
<many-to-one name="company" column="COMPANY_ID" class="mypack.Company"/> <!-- 關聯重複定義 -->
</class>
</hibernate-mapping>
<hibernate-mapping>
<class name="mypack.SalariedEmployee" table="SALARIED_EMPLOYEES">
<id name="id" column="ID"><generator class="increment"/></id>
<property name="name" column="NAME"/>
<property name="salary" column="SALARY" type="double"/>
<many-to-one name="company" column="COMPANY_ID" class="mypack.Company"/>
</class>
</hibernate-mapping>
<hibernate-mapping>
<class name="mypack.Company" table="COMPANIES">
<id name="id" column="ID"><generator class="increment"/></id>
<property name="name" column="NAME"/>
<set name="employees" inverse="true" lazy="true">
<key column="COMPANY_ID"/>
<one-to-many class="mypack.Employee"/> <!-- 注意:這裡引用父類/介面 -->
</set>
</class>
</hibernate-mapping>
name、id、company 關聯在每個子類映射中完整重複定義。Employee (抽象類) 沒有 .hbm.xml,不參與持久化。<one-to-many class="mypack.Employee"/> 引用抽象父類,但實際運行時集合為空(不支援多態關聯)。config.addClass(HourlyEmployee.class).addClass(SalariedEmployee.class),無需註冊 Employee。
圖示:Company 1:N HourlyEmployee/SalariedEmployee,但無共享父表。
increment 生成器會產生重複 ID。生產環境必須使用共享序列、uuid.hex 或資料庫原生 identity/sequence 保證跨表唯一。Employee 加字段 → 需同步修改 所有子類映射文件 及 所有子表結構。from Employee 會拋異常 (抽象類) 或只查 Employee 表 (具體類),永遠無法自動查詢子表。此策略將「繼承」純粹視為代碼復用,數據層完全扁平化。理解其映射冗餘與多態缺失,是為掌握進階策略鋪路。