Hibernate继承关系的实体设计的两种方法

本文介绍使用Hibernate框架实现多表继承的两种方法:通过独立的子表存储特殊属性及在一个表中使用标志区分不同子类。涵盖数据库表设计、Java类定义、映射文件配置及测试代码。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

 
1 对于父类和子类分别对应数据库中的一个表,父类表中的字段是公共的属性,子类表中是特殊的属性。
数据库表:
父表: titem 字段:id (id) name (名称) manufacturer (产地)
               子表1:ibook 字段:id (id) pagecount(页数)
         子表2:idvd  字段:id (id) regioncode (编号)
(1)    创建数据库:
--删除数据库表
droptable Titem;
droptable TBook;
droptable TDVD;
--创建数据库表
createtable Titem(
 id varchar(32) notnullprimarykey,
 namevarchar(20)notnull,
 manufacturer varchar()
);
createtable TBook(
 id varchar(32) notnullprimarykey,
 pagecount int
);
createtable TDvd(
 id varchar(32) notnullprimarykey,
 regioncode varchar(2)
);
2)编写类文件:
TItem类:
package hibernate.hbu;
publicclass TItem {
 
    private String id;
 
    private String name;
 
    private String manufacturer;
 
    public String getId() {
       returnid;
    }
 
    publicvoid setId(String id) {
       this.id = id;
    }
 
    public String getManufacturer() {
       returnmanufacturer;
    }
 
    publicvoid setManufacturer(String manufacturer) {
       this.manufacturer = manufacturer;
    }
 
    public String getName() {
       returnname;
    }
 
    publicvoid setName(String name) {
       this.name = name;
    }
}
TBook类:
package hibernate.hbu;
 
publicclass TBook extends TItem {
 
    privateintpagecount;
 
    publicint getPagecount() {
       returnpagecount;
    }
 
    publicvoid setPagecount(int pagecount) {
       this.pagecount = pagecount;
    }
 
}
 
TDvd类:
package hibernate.hbu;
 
publicclass TDvd extends TItem {
 
    private String regioncode;
 
    public String getRegioncode() {
       returnregioncode;
    }
 
    publicvoid setRegioncode(String regioncode) {
       this.regioncode = regioncode;
    }
}
3)映射文件:titem.hbm.xml
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<!--
    Mapping file autogenerated by MyEclipse Persistence Tools
-->
<hibernate-mapping>
    <class name="hibernate.zyl.TItem" table="titem" catalog="test">
       <id name="id" type="java.lang.String">
           <column name="id" length="32" />
           <generator class="assigned" />
       </id>
       <property name="name" type="java.lang.String">
           <column name="name" length="20" not-null="true" />
       </property>
       <property name="manufacturer" type="java.lang.String">
           <column name="manufacturer" length="255" />
       </property>
       <joined-subclass name="hibernate.zyl.TBook" table="tbook">
           <key column="id"></key>
           <property name="pagecount" type="java.lang.Integer"
              column="pagecount">
           </property>
       </joined-subclass>
       <joined-subclass name="hibernate.zyl.TDvd" table="tdvd">
           <key column="id"></key>
           <property name="regioncode" type="java.lang.String"
              column="regioncode">
           </property>
       </joined-subclass>
    </class>
</hibernate-mapping>
3)测试类: Test.java
     package hibernate.zyl;
 
import hibernate.sessionFactory.HibernateSessionFactory;
import org.hibernate.Session;
import org.hibernate.Transaction;
publicclass Test {
 
    /**
     *@paramargs
     */
    publicstaticvoid main(String[] args) {
       // TODO Auto-generated method stub
 
       Session session = HibernateSessionFactory.getSession();
       Transaction tr = null;
 
       // TDvd dvd = new TDvd();
       // dvd.setId("001");
       // dvd.setRegioncode("0");
       // dvd.setManufacturer("hebei");
       // dvd.setName("net");
       // dvd.setRegioncode("6");
 
       TBook book = new TBook();
       book.setId("005");
       book.setName("Java");
       book.setManufacturer("机械工业");
       book.setPagecount(66);
 
       tr = session.beginTransaction();
       // session.save(dvd);
       session.save(book);
       tr.commit();
    }
}
 
2 在一个表中实现:
表: Titem 字段:id  name  category(特殊的标志位) manufacturer(产地)
 pagecode(页数) regioncode(编号)
 category的值是1时,我们让此条记录指向一个TBook类,其中pagecode是具体的值,而regioncode的值是空的;当category的值是2时,我们让此条记录指向一个TDvd类,其中pagecode是空的,而regioncode的值是具体的值
 
(1)       创建数据库:
 --删除数据库表
droptable Titem;
--创建数据库表
createtable Titem(
 id varchar(32) notnullprimarykey,
 namevarchar(20)notnull,
 category varchar(50) notnull,
 manufacturer varchar(50),
 regioncode varchar(2),
 pagecount int
);
(2)       编写类文件:
 类文件的内容和前面的相同,不过要指出:虽然在表中增加了一个category字段但我们并不在类文件中增加这个属性,只是在映射文件中加以配置。
3)映射文件:titem.hbm.xml
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<!--
    Mapping file autogenerated by MyEclipse Persistence Tools
-->
<hibernate-mapping>
    <class name="hibernate.zyl.TItem" table="titem" catalog="test">
       <id name="id" type="java.lang.String">
           <column name="id" length="32" />
           <generator class="assigned" />
       </id>
       <discriminator column="category" type="java.lang.String"
           not-null="true" length="50">
       </discriminator>
       <property name="name" type="java.lang.String">
           <column name="name" length="20" not-null="true" />
       </property>
       <property name="manufacturer" type="java.lang.String">
           <column name="manufacturer" length="50" />
       </property>
        <subclass name="hibernate.zyl.TBook" discriminator-value="1">
           <property name="pagecount" column="pagecount"
              type="java.lang.Integer">
           </property>
       </subclass>
       <subclass name="hibernate.zyl.TDvd" discriminator-value="2">
           <property name="regioncode" column="regioncode"
              type="java.lang.String">
           </property>
       </subclass>
    </class>
</hibernate-mapping>
3)测试类: Test.java
    package hibernate.zyl;
 
import java.util.Iterator;
 
import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.Transaction;
 
import sessionFactory.HibernateSessionFactory;
 
publicclass Test {
 
    /**
     *@paramargs
     */
    publicstaticvoid main(String[] args) {
       // TODO Auto-generated method stub
 
       Session session = HibernateSessionFactory.getSession();
       Transaction tr = null;
 
       // TBook book = new TBook();
       // book.setId("009");
       // book.setName("Java");
       // book.setManufacturer("石家庄");
       // book.setPagecount(2);
 
       // TDvd dvd = new TDvd();
       // dvd.setId("012");
       // dvd.setManufacturer("北京海淀");
       // dvd.setName("Advd");
       // dvd.setRegioncode("2");
 
       // tr = session.beginTransaction();
       // session.save(dvd);
       // tr.commit();
 
       TDvd dvd = null;
       TItem item = null;
       String hql = "from TItem t where t.id=?";
       Query q = session.createQuery(hql);
       q.setParameter(0, "012");
       Iterator it = q.list().iterator();
       while (it.hasNext()) {
           dvd = (TDvd) it.next();
       }
 
       System.out.println(dvd.getManufacturer());
    }
 
}
 
 
 
 
 
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值