Hibernate之基于主键映射的一对一关联关系

时间:2023-03-09 18:08:05
Hibernate之基于主键映射的一对一关联关系

1. 基于主键的映射策略:指一端的主键生成器使用foreign策略,表明根据”对方”的主键来生成自己的主键,自己并不能独立生成主键.并用<param> 子元素指定使用当前持久化类的哪个属性作为“对方”

2. 采用foreign主键生成器策略的一端增加one-to-one元素映射关联属性,其one-to-one属性还应增加constrained=“true”属性;另一端增加one-to-one元素映射关联属性

3. constrained(约束):指定为当前持久化类对应的数据库表的主键添加一个外键约束,引用被关联的对象(“对方”)所对应的数据库表主键

4. 单元测试示例代码:

须要被映射的2个实体类:

public class Manager {

	private int mgrId;
private String mgrName;
private Department dept;
public int getMgrId() {
return mgrId;
}
public void setMgrId(int mgrId) {
this.mgrId = mgrId;
}
public String getMgrName() {
return mgrName;
}
public void setMgrName(String mgrName) {
this.mgrName = mgrName;
}
public Department getDept() {
return dept;
}
public void setDept(Department dept) {
this.dept = dept;
} }
public class Department {

	private int deptId;
private String deptname;
private Manager mgr; public int getDeptId() {
return deptId;
}
public void setDeptId(int deptId) {
this.deptId = deptId;
}
public String getDeptname() {
return deptname;
}
public void setDeptname(String deptname) {
this.deptname = deptname;
}
public Manager getMgr() {
return mgr;
}
public void setMgr(Manager mgr) {
this.mgr = mgr;
} }

2个实体类分别对于那个的hbm映射文件

<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<!-- Generated 2015-9-25 22:25:22 by Hibernate Tools 3.4.0.CR1 -->
<hibernate-mapping>
<class name="com.elgin.hibernate.one2one.primary.Manager" table="MANAGER">
<id name="mgrId" type="int">
<column name="MGRID" />
<generator class="native" />
</id>
<property name="mgrName" type="java.lang.String">
<column name="MGRNAME" />
</property>
<one-to-one name="dept" class="com.elgin.hibernate.one2one.primary.Department"></one-to-one>
</class>
</hibernate-mapping>
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<!-- Generated 2015-9-25 22:25:22 by Hibernate Tools 3.4.0.CR1 -->
<hibernate-mapping package="com.elgin.hibernate.one2one.primary">
<class name="Department" table="DEPARTMENT">
<id name="deptId" type="int">
<column name="DEPTID" />
<!-- 使用外键的方式来生成当前主键 -->
<generator class="foreign" >
<!-- property属性指定当前实体化类的哪一个属性的主键作为外键 -->
<param name="property">mgr</param>
</generator>
</id>
<property name="deptname" type="java.lang.String">
<column name="DEPTNAME" />
</property>
<one-to-one name="mgr" class="Manager" constrained="true"></one-to-one>
</class>
</hibernate-mapping>

5. 单元测试类:

public class HibernateTest2 {

	//如此声明只为方便测试,生产环境不能这么用
private SessionFactory sessionFactory;
private Session session;
private Transaction transcation; @Before
public void init(){
Configuration cfg=new Configuration().configure();
ServiceRegistry serviceRegistry=new ServiceRegistryBuilder().applySettings(cfg.getProperties()).buildServiceRegistry();
sessionFactory=cfg.buildSessionFactory(serviceRegistry);
session=sessionFactory.openSession();
transcation=session.beginTransaction();
} @Test
public void testOne2OnePrimarySave(){
Manager mgr=new Manager();
mgr.setMgrName("XXXfffff"); Department dept=new Department();
dept.setDeptname("软件开发部rrr"); dept.setMgr(mgr);
mgr.setDept(dept);
//先插入那一端都不会发出update语句
session.save(dept);
session.save(mgr);
} @Test
public void testOne2OnePrimaryGet(){
//1.依旧使用懒加载,默认情况下不直接查询出关联的对象,而是返回对应的代理对象,等到使用的时候再来初始化
//2.所以在session关闭的情况下仍旧会出现懒加载异常
Department dept=(Department) session.get(Department.class, 1);
System.out.println(dept.getDeptname()); //3.在查询没有外键的实体对象时使用左外连接一并查询出其关联的对象并初始化
Manager mgr=(Manager) session.get(Manager.class, 1);
System.out.println(mgr.getMgrName());
} @After
public void destory(){
transcation.commit();
session.close();
sessionFactory.close();
} }