我们以部门和员工的关系为例讲解一对多关联关系映射时,删除部门时,如果部门有关联的员工且inverse属性为false,那么由于可以维护关联关系,它就会先把关联的员工的外键列设为null值,再删除自己。但是此刻希望删除部门时,就附带着把该部门下的所有员工都删掉,这时就需要引入cascade属性了。

级联(cascade)

当Hibernate持久化一个临时对象时,在默认情况下,它不会自动持久化所关联的其他临时对象,而是会抛出TransientObjectException。如果设定many-to-one元素的cascade属性为save-update的话,可实现自动持久化所关联的对象。如:

1,<many-to-one name="customer"
2,column="CUSTOMER_ID"
3,class="..Customer"
4,cascade="save-update"
5, not-null="true" />

级联指的是当主控方执行操作时,关联对象(被动方)是否同步执行同一操作。

级联风格

每个Hibernate session的基本操作包括persist()、merge()、saveOrUpdate()、delete()、lock()、refresh()、evict()、replicate(),这些操作都有对应的级联风格(cascade style)。这些级联风格(cascade style)风格分别命名为persist、merge、save-update、delete、lock、refresh、evict、replicate。

级联风格 Session中的方法
persist persist()
merge merge()
save-update save()、update()、saveOrUpdate()
delete delete()
lock lock()
refresh refresh()
evict evict()
replicate replicate()

如果你希望一个操作被顺着关联关系级联传播,你必须在映射文件中指出这一点。

指定级联风格:

1,<one-to-one name="person" cascade="persist" />

级联风格(cascade style)是可组合的:

1,<one-to-one name="person" cascade="persist,delete" />

你可以使用cascade=”all”来指定全部操作都顺着关联关系级联(cascaded)。默认值是cascade=”none”,即任何操作都不会被级联(cascaded)。 
在对象/关系映射文件中,用于映射持久化类之间关联关系的元素,如<set><many-to-one><one-to-one>都有一个cascade属性。 

案例分析——cascade属性

还是回到开头我们提出的需求,即删除部门时,就附带着把该部门下的所有员工都删掉。要满足这个需求,我们最好新建一个普通java工程,如Hibernate_Test,然后在cn.itcast.f_hbm_oneToManyb包下新建持久化类——Department.java和Employee.java。 
持久化类——Department.java的代码如下:

/*** 部门* @author li ayun**/
public class Department {private Integer id;private String name;private Set<Employee> employees = new HashSet<Employee>(); // 关联的很多个员工public Integer getId() {return id;}public void setId(Integer id) {this.id = id;}public String getName() {return name;}public void setName(String name) {this.name = name;}public Set<Employee> getEmployees() {return employees;}public void setEmployees(Set<Employee> employees) {this.employees = employees;}@Overridepublic String toString() {return "[Department: id=" + id + ", name=" + name + "]";}
}

持久化类——Employee.java的代码如下:

/*** 员工* @author li ayun**/
public class Employee {private Integer id;private String name;private Department department; // 关联的部门对象public Integer getId() {return id;}public void setId(Integer id) {this.id = id;}public String getName() {return name;}public void setName(String name) {this.name = name;}public Department getDepartment() {return department;}public void setDepartment(Department department) {this.department = department;}@Overridepublic String toString() {return "[Employee: id=" + id + ", name=" + name + "]";}
}

由于我们先前就分析过各个持久化类在数据库中所对应的表的结构,所以我们很容易就写出各个持久化类相应的映射配置文件了。 
先在cn.itcast.f_hbm_oneToMany包中创建Department类对应的映射配置文件——Department.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.itcast.f_hbm_oneToMany"><class name="Department" table="department"><id name="id"><generator class="native"></generator> </id><property name="name" /><!-- employees属性,Set集合,表达的是本类与Employee的一对多的关系class属性:关联的实体类型key子元素:对方表中的外键列(多方的哪个表)inverse属性:默认为false,表示本方维护关联关系。如果为true,表示本方不维护关联关系。只是影响是否能设置外键列的值(设成有效值或是null值),对获取信息没有任何影响。cascade属性:默认为none,代表不级联。级联是指操作主对象时,对关联的对象也做相同的操作。可设为:delete,save-update,all,none,...--><set name="employees" cascade="save-update,delete"><key column="departmentId"></key><one-to-many class="Employee"/></set></class>
</hibernate-mapping>

<set>元素中设置cascade=”save-update,delete”,即表示只须保存/修改某部门,该部门下的所有员工都将保存/修改,或者删除部门时,就附带着把该部门下的所有员工都删掉。 
然后也是在该包中创建Employee类对应的映射配置文件——Employee.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.itcast.f_hbm_oneToMany"><class name="Employee" table="employee"><id name="id"><generator class="native"></generator> </id><property name="name" type="string" column="name" /><!-- department属性,表达的是本类与Department的多对一的关系class属性:关联的实体类型column属性:外键列(引用关联对象的表的主键)--><many-to-one name="department" class="Department" column="departmentId"></many-to-one></class>
</hibernate-mapping>

接下来,我们从以下2个方面来编写代码进行测试:

  • 保存新数据,并有关联关系。
  • 删除对象,看对关联对象的影响。

所以,我们要在cn.itcast.f_hbm_oneToMany包中编写一个单元测试类——Application.java。

public class Application {private static SessionFactory sessionFactory = new Configuration() //.configure() //.addClass(Department.class) // 添加Hibernate实体类(加载对应的映射文件).addClass(Employee.class) // 添加Hibernate实体类(加载对应的映射文件).buildSessionFactory();// 保存,有关联关系@Testpublic void testSave() {Session session = sessionFactory.openSession();session.beginTransaction();// -------------------------------------------// 新建对象Department department = new Department();department.setName("开发部");Employee employee1 = new Employee();employee1.setName("张三");Employee employee2 = new Employee();employee2.setName("李四");// 关联起来employee1.setDepartment(department); // 告诉员工他属于哪个部门employee2.setDepartment(department);department.getEmployees().add(employee1); // 告诉部门它有两个关联的员工department.getEmployees().add(employee2);// 保存session.save(department); // 保存部门// -------------------------------------------session.getTransaction().commit();session.close();}// 删除对象,对关联对象的影响@Testpublic void testDelete() {Session session = sessionFactory.openSession();session.beginTransaction();// -------------------------------------------// 删除部门方(一方)Department department = (Department) session.get(Department.class, 1);session.delete(department);// -------------------------------------------session.getTransaction().commit();session.close();}
}

这样,当保存部门时,会级联保存该部门下的所有员工,或者删除部门时,就会级联删除该部门下的所有员工。我们也可以配置员工级联删除部门,但这样做,在业务上是极不合理的。

总结

一般是多对一和多对多的时候不使用级联,一对一和一对多可以使用级联,这两种情况使用级联比较多,总结来说,这个对象归你控制,你就能够级联,它不归你一个人所有,那你就不要级联。 
还有一点要注意,inverse属性和cascade属性毛关系都没有。

级联(cascade)相关推荐

  1. (7) hibernate之级联cascade和关系维持inverse

    hibernate的关联关系,重点在理解级联cascade和inverse 1.cascade一般用在级联保存,级联更新,级联删除上      1.1cascade注解有两种,一种是基于hiberna ...

  2. jpa级联添加_jpa级联(Cascade)操作

    由于 重复性的操作十分烦琐,尤其是在处理多个彼此关联对象情况下,此时我们可以使用级联(Cascade)操作.级联 在关联映射中是个重要的概念,指当主动方对象执行操作时,被关联对象(被动方)是否同步执行 ...

  3. 人脸检测之Haar-like,Adaboost,级联(cascade)

    最新版本整理完毕,见: http://face2ai.com/MachineLearning-Haar-like-Adaboost-cascade 0:写在前面的话           写在前面的牢骚 ...

  4. Hibernate一对多关联映射及cascade级联操作

    我们以客户(Customer)与订单(Order)为例 实体类创建 Order订单实体类 //订单-----多的一方 public class Order {private Integer id;pr ...

  5. JPA规范:一对多、一对一、多对多的双向关联与级联操作以及JPA联合主键

    通常在企业开发中,开发Dao层有两种做法:  (1)先建表,后再根据表来编写配置文件和实体bean.使用这种方案的开发人员受到了传统数据库建模的影响.  (2)先编写配置文件和实体bean,然后再生成 ...

  6. oracle中删除级联方法,Oracle 外键级联删除

    Oracle 外键级联删除 日期:2010年5月22日 作者: 近来软件系统中要删除一条记载,就要关联到同时删除好多张表,它们之间还存在着约束联络.所以思索到在树立表时加上约束联络,细致内容如下: S ...

  7. mysql中的级联删除的语句_级联删除sql语句-数据库级联删除语句-sql删除语句

    SQl语句的级联删除问题 删除应该有顺序 1,删除link表 delete from ref,link where ref.link_code=link.link_code and link_id=? ...

  8. TI毫米波级联雷达评估板 MMWCAS-DSP-EVM 和MMWCAS-RF-EVM

    1. 前言 本文主要是TI的MMWCAS-DSP-EVM 和MMWCAS-RF-EVM 两块评估板的一些使用心得和毫米波雷达的学习总结. 2. 相关原理 毫米波(mmWave)是一类使用短波长电磁波的 ...

  9. Oracle外键约束如何同时更新,SQL与ORACLE的外键约束-级联更新和删除

    /* SQL与ORACLE的外键约束--级联删除 最近软件系统中要删除一条记录,就要关联到同时删除好多张表,他们之间还存在着约束关系.所以考虑到在创建表时加上约束关系,具体如下: SQL的外键约束可以 ...

  10. oracle 外键 更新,Oracle外键级联删除与更新

    2012年Oracle:Oracle外键级联删除与更新 比来软件系统中要删除一标识表记标帜录,就要联系关系到同时删除良多若干好多张表,它们之间还存在着约束关系.所以考虑到在建树表时加上约束关系,具体内 ...

最新文章

  1. Chapter 7. Testing and Debugging
  2. 建立注册DLL和反注册DLL文件的快捷方式
  3. 干掉系统害群之马 轻轻松松“杀”进程
  4. 通俗易懂的Redis数据结构基础教程
  5. 如果你的名字,当然【随机】给你
  6. 音视频技术开发周刊 | 165
  7. javascript 不让成为nan_这10个JavaScript面试题,看看你会几个?
  8. 解决postman请求乱码问题
  9. Centos7 安装Mysql5.7
  10. Windows 8.1 升级到专业版
  11. 解决 SpringBoot 在 JDK8 中 LocalDateTime (反)序列化问题
  12. Airflow 中文文档:用Dask扩展
  13. app、web和接口测试测试流程
  14. 三,linux系统的由来
  15. 处理PHP字符串的10个简单方法
  16. eclipse经常出现弹窗Refreshing workspace
  17. win10开机字体变大bug
  18. 《微观经济学》第一章
  19. 家庭服务器搭建,NAS存储
  20. java定义一个short_JDK源码解读第七章:java.lang.Short

热门文章

  1. 习题七-斐波那契数列
  2. Python数据分析与应用_从数据获取到可视化题库及答案
  3. 跨境电商RPA是什么意思?用PRA工具能做啥?
  4. FANUC机器人有关执行程序的停止和恢复的说明
  5. C语言编写一个函数,实现计算并返回一个整数的平方(或立方)
  6. will-change的使用
  7. 动态规划问题解决方法及示例
  8. 回文是指正读反读均相同的字符序列,如“abba”和“abdba”均是回文,但“good”不是回文。试写一个算法判定给定的字符向量是否为回文。(提示:将一半字符入栈)
  9. week2-二分和二分搜索
  10. Object.assign与vue $set