06章 映射一对多双向关联关系、以及cascade、inverse属性
当类与类之间建立了关联,就可以方便的从一个对象导航到另一个对象。或者通过集合导航到一组对象。例如:
对于给定的Emp对象,如果想获得与它关联的Dept对象,只要调用如下方法
Dept dept=emp.getDept(); //从Emp对象导航到关联的Dept对象
以Dept(部门)类和Emp(员工)类为例:
一、配置双向一对多关联
需在Dept类中增加一个集合类型的emps属性


private Set<Emp> emps=new HashSet<Emp>();
public Set<Emp> getEmps() {
return emps;
}
public void setEmps(Set<Emp> emps) {
this.emps = emps;


如何在映射文件中映射集合类型的emps属性。由于在Dept表中没有直接与emps属性对应的字段。因此不能用<property>元素来映射emps属性,而要使用<set>元素:
<set name="emps">
<key column="deptNo"></key> <!-- 多的一方 emp外键 -->
<one-to-many class="Emp" />
</set>
解析:
<set>元素的name属性:设定持久化类的属性名。此处为Dept类的emps属性。
<set>元素还包含两个子元素:
①<key>元素:column属性设定与所关联的持久化类对应的表的外键
②<one-to-many>元素:class属性设定与所关联的持久化类
hibernate根据以上映射代码获得以下信息:
①<set>元素表明Dept类的emps属性为java.util.Set集合类型
②<one-to-many>子元素表明emps集合中存放的是一组Emp对象
③<key>子元素表明EMP表通过外键DEPTNO参照Dept表
Dept.hbm.xml代码:


<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd">
<hibernate-mapping package="cn.happy.onetomanydouble">
<class name="Dept" table="DEPT">
<id name="deptNo">
<generator class="sequence">
<param name="sequence">SEQ_NUM</param>
</generator>
</id>
<property name="deptName"/> <!-- 一对多一个配置,一个部门有N个员工 -->
<!--
inverse="false" 主动方 维护关联关系 inverse="true" 不维护关联关系(不干扰Emp的外键生成)
-->
<set name="emps" cascade="save-update">
<key column="deptNo"></key> <!-- 多的一方 emp外键 -->
<one-to-many class="Emp" />
</set> </class>
</hibernate-mapping>


Emp.hbm.xml:


<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd">
<hibernate-mapping package="cn.happy.onetomanydouble">
<class name="Emp" table="EMP">
<id name="empId">
<generator class="sequence">
<param name="sequence">SEQ_NUM</param>
</generator>
</id>
<property name="empName" type="string"/> <!-- 植入一个Dept对象 : 多对一-->
<many-to-one name="dept" class="Dept" column="deptNo"></many-to-one>
</class>
</hibernate-mapping>


进而编写测试类:Test 即可拿到deptNo为1的员工姓名


public class Test2 {
Session session;
Transaction tx;
@After
public void afterTest(){
tx.commit();
HibernateUtil.CloseSession();
}
@Before
public void initData(){
session=HibernateUtil.getSession();
tx=session.beginTransaction();
}
/*
* 一对多双向关联测试
*/
@Test
public void oneToManyDoubleTest(){
//获取员工集合
Dept dept=(Dept)session.load(Dept.class,1);
Set<Emp> emps =dept.getEmps();
for (Emp emp : emps) {
System.out.println(emp.getEmpName());
}
}


二、cascade属性
none:当Session操纵当前对象时,忽略其他关联的对象。它是cascade属性的默认值.
Save-update:当通过Session的save()、update()及saveOrUpdate()方法来保存或更新当前对象时,级联保存所有关联的新建的瞬时状态的对象,并且级联更新所有关联的游离状态的对象。
Delete:当通过Session的delete()方法删除当前对象时,会级联删除所有关联的对象。
当通过Session的delete()方法删除当前对象时,会级联删除所有关联的对象。
All:包含save-update,delete的行为。
解析:
级联也就是说当我们保存持久化对象A的时候自动帮我们保存持久化对象B。
问题:cascade属性写在什么位置?
注:一对一或者多对一的时候,直接写在标签上,其他的写在set标签上。
如何实现添加部门的同时自动添加员工?
解析:可以使用cascade(级联)方式

Test:双向关联 通过add()将新建的员工对象添加部门下


public class Test3 {
Session session;
Transaction tx;
@After
public void afterTest(){
tx.commit();
HibernateUtil.CloseSession();
}
@Before
public void initData(){
session=HibernateUtil.getSession();
tx=session.beginTransaction();
}
/*
*cascade
*/
@Test
public void oneTest(){
//构建一个部门
Dept dept=new Dept();
dept.setDeptName("财务部");
//构建一个员工
Emp emp=new Emp();
emp.setEmpName("张三");
//指定员工隶属的部门
emp.setDept(dept);
// setXXX 部门下的员工
dept.getEmps().add(emp);
//save
session.save(dept);
session.save(emp);
}
}


三、<Set>元素下的inverse属性(反转)
inverse属性指定了关联关系中的方向。
inverse设置为false,则为主动方,由主动方负责维护关联关系,默认是false 。
注意:inverse 决定是否把对对象中集合的改动反映到数据库中,所以inverse只对集合起作用,也就是只对one-to-many或many-to-many有效(因为只有这两种关联关系包含集合,而one-to-one和many-to-one只含有关系对方的一个引用)。
代码同理:
说明:如果我既给员工指定了自己所属的部门,又将员工添加到部门集合中。那么这个时候reverse不设置,生成以下sql
inverse设置为true,不负责维护关联关系

第二条insert语句已经在员工表中指定了自己所属的部分,没有必要再向数据库发送一条update指令。
将inverse设置成true后,生成的语句如下图所示。

06章 映射一对多双向关联关系、以及cascade、inverse属性的更多相关文章
- Hibernate映射一对多双向关联关系及部门关联属性
一对多双向关联关系:(Dept/Emp的案例) 既可以根据在查找部门时根据部门去找该部门下的所有员工,又能在检索员工时获取某个员工所属的部门. 步骤如下: 1.构建实体类(部门实体类加set员工集合) ...
- 映射一对多双向关联关系 cascade、inverse、属性
当类与类之间建立了关联,就可以方便的从一个对象导航到另一个对象.或者通过集合导航到一组对象.例如: 对于给定的Emp对象,如果想获得与它关联的Dept对象,只要调用如下方法 Dept dept=emp ...
- Hibernate映射多对多双向关联关系(小案例)
多对多双向关联关系(Project(工程)/Emp(员工)为案例): 步骤如下: 1.创建Project类,并需要定义集合类型的Emp属性 public class Project { //编号 pr ...
- Hibernate 建立一对多双向关联关系
下面内容整理自<精通Hibernate>第二版 注:既然是双向关联."一对多双向关联"和"多对一双向关联"是同一回事. 对象位于内存中,在内存中从一 ...
- Hibernate逍遥游记-第5章映射一对多-02双向(<set>、<key>、<one-to-many>、inverse、cascade="all-delete-orphan")
1. <?xml version="1.0"?> <!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hi ...
- Hibernate -- 映射多对多双向关联关系
1. 示例代码: Student.java package cn.itcast.many2many; import java.util.HashSet; import java.util.Set; @ ...
- Hibernate框架关系映射一对多双向关联
直入主题,首先大配置常规配置, 这里住要说关联关系,大配置不多少,而且jar包默认添加好,笔者用的是idea2016. 然后我们知道关联关系主要是在小配置添加节点来配置属性.个人认为关联映射,就是对应 ...
- Hibernate逍遥游记-第5章映射一对多-01单向<many-to-one>、cascade="save-update"、lazy、TransientObjectException
1. <?xml version="1.0"?> <!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hi ...
- 攻城狮在路上(壹) Hibernate(五)--- 映射一对多关联关系
关联是有方向的,包含单向关联和双向关联.分别讨论.本文以客户Customer和订单Order来进行讨论:一个Customer有多个Order,每个Order对应一个Customer. Customer ...
随机推荐
- Java集合概述
容器,是用来装东西的,在Java里,东西就是对象,而装对象并不是把真正的对象放进去,而是指保存对象的引用.要注意对象的引用和对象的关系,下面的例子说明了对象和对象引用的关系. String str = ...
- php实现设计模式之 工厂方法模式
<?php /* * *工厂方法模式,创建型模式 定义一个用于创建对象的工厂接口,让子类决定实例化哪一个类.Factory Method使用一个类的实例化延迟到其子类 * * 四个角色: * 工 ...
- java反编译获取源码
最近在研究反射,想做一个东西,把运行的java程序饭编译(Decompile)成.java文件.现思路如下: 1.写出程序反编译一个类 2.将所有类反编译 3.java代码注入一个正在运行的java程 ...
- Dog_Hybird的诞生
起因 开玩笑说“iOS搞不动了”,另外一方面iOS组的哥哥们给力,少一个我也妥妥的.又听闻web前端组来了一个不得了的人物,“老司机,带带我”这种机会不能错过,1个多月前就申请转web前端了.开始是苦 ...
- 钉钉js依赖库学习
看别人用的依赖库的好处在于,你知道有什么可以用,什么可以借鉴.(钉钉——协作桌面应用) PS:人最怕是不知道,而不是你不会. 1. jQuery 钉钉使用了1.9.1版本的jQuery,jQuery作 ...
- C#操作Excell常用方法
这是在博客园看的文章,写的很好,所以转一下,方便自己以后用到的时候可以随时查看. range.NumberFormatLocal = "@"; //设置单元格格式为文本 r ...
- iOS 学习 - 25 ImageIO 播放 GIF
一.给原生的 UIImageView 添加类别来支持 GIF 播放 GIF 动态图片文件中包含了一组图片及信息,信息主要记录着每一帧图片播放的时间,我们如果获取到了 gif 文件中所有的图片同时又获取 ...
- configure Git to accept a particular self-signed server certificate for a particular https remote
get the self signed certificate put it into some (e.g. ~/git-certs/cert.pem) file set git to trust t ...
- ORACLE会话连接进程三者总结
概念介绍 通俗来讲,会话(Session) 是通信双方从开始通信到通信结束期间的一个上下文(Context).这个上下文是一段位于服务器端的内存:记录了本次连接的客户端机器.通过哪个应用程序.哪个用户 ...
- ORA-01012: not logged on
关于ORA-01012这个错误,惜分飞的博客ORA-01012: not logged on里面已经做了一些介绍,原因就不多说了,看看他的描述说明: 现象说明: 1)终于发现了ORA-01012错误, ...