1.单向一对多(@OneToMany)关联是比较少用的(一般用双向一对多代替)。

2.实体类:

1端:Publishers.java

public class Publishers {

    private Integer id;
private String Name;
//集合属性
private Set bks = new HashSet<>();
//忽略getter和setter方法
...
}

n端:Books.java

public class Books {

    private Integer Id;
private String Title;
private String Author;
private String ISBN;
private int WordCount;
private double UnitPrice;
private String ContentDescription;
//忽略getter和setter方法
...
}

3.映射文件

1端:Publishers.hbm.xml

<hibernate-mapping>

    <class name="com.withXml.oneTomany.entity.Publishers" table="PUBLISHERS">

        <id name="id" type="java.lang.Integer" access="field">
<column name="ID" />
<generator class="native" />
</id> <property name="Name" type="java.lang.String">
<column name="NAME" />
</property>
<!-- 配置单向一对多配置,在一的一方进行配置 -->
<!--set节点:
cascade(级联)级联的意思是指两个对象之间的操作联运关系,对一个对象执行了操作之后,
对其指定的级联对象也需要执行相同的操作,取值:all,none,save_update,delete。
1.all:代码在所有情况下都执行级联操作
2.none:在所有情况下都不执行级联操作
3.save-update:在保存和更新的情况下执行级联操作
4.delete:在删除的时候执行级联操作
name:保存多端对象集合的属性。
table:多端的数据表。
<key>:指定多端的外键。
-->
<set name="bks" lazy="false" table="BOOKS" cascade="save-update,delete">
<key column="PUBLISHER_ID"></key>
<one-to-many class="com.withXml.oneTomany.entity.Books"/>
</set>
</class>
</hibernate-mapping>

n端:Books.hbm.xml

<hibernate-mapping package="com.withXml.oneTomany.entity">

    <class name="Books" table="BOOKS">

        <id name="Id" type="java.lang.Integer" access="field">
<column name="ID" />
<generator class="native" />
</id> <property name="Title" type="java.lang.String">
<column name="TITLE" />
</property> <property name="Author" type="java.lang.String">
<column name="AUTHOR" />
</property> <property name="ISBN" type="java.lang.String">
<column name="ISBN" />
</property> <property name="WordCount" type="integer">
<column name="WORD_COUNT"/>
</property> <!-- 映射数据表字段你的类型,可以在property 里面使用type设置,也可以在column里面使用 sql-type设置-->
<property name="UnitPrice">
<column name="UNIT_PRICE" sql-type="double" />
</property> <property name="ContentDescription" type="java.lang.String">
<column name="CONTENT_DESCRIPTION" />
</property> </class>
</hibernate-mapping>

5.CRUD测试

①保存

/**
* 添加操作
* 添加图书和出版社信息
*/
@Test
public void testOneToManySave(){
//新建出版社对象
Publishers publisher = new Publishers();
publisher.setName("北京大学出版社");
//新建图书对象
Books book = new Books();
book.setTitle("大学英语");
book.setISBN("2018012103");
book.setAuthor("李玲");
book.setWordCount(10000);
book.setUnitPrice(95.5);
book.setContentDescription("无"); //新建图书对象
Books book2 = new Books();
book2.setTitle("管理学");
book2.setISBN("2018012104");
book2.setAuthor("张青");
book2.setWordCount(10000);
book2.setUnitPrice(95.5);
book2.setContentDescription("无"); //设定关联关系,从多的一端维护关系,想要从多端维护关联关系需要在多端配置many-to-one,三条insert语句,推荐使用这种方式
//book.setPublisher(publisher);
//book2.setPublisher(publisher); //设定关联关系,从一的一端维护关系,想要从一端维护关联关系需要在一端配置one-to-many,三条insert语句,两条update语句,不推荐使用这种方式,因为这里需要演示1对n关联关系,所以使用该方法
publisher.getBks().add(book);
publisher.getBks().add(book2); //执行保存操作,先保存1的一端,在保存n的一端
session.save(publisher);
session.save(book);
session.save(book2); }

②获取

/**
* 获取操作
* 通过出版社获取图书信息
*/
@Test
public void testOneToManyGet(){
//根据id获取出版社对象
Publishers publisher = (Publishers) session.get(Publishers.class, 1);
System.out.println(publisher.getName() + "出版的图书有:");
//获取集合的迭代器
Iterator iterators = publisher.getBks().iterator();
while(iterators.hasNext()){
Books book = (Books) iterators.next();
System.out.println(book.getTitle());
} }

③修改

/**
* 修改操作
* 功能:修改id为1的出版社的名字
*/
@Test
public void testOneToManyUpdate(){
Publishers publisher = (Publishers) session.get(Publishers.class, 2);
publisher.setName("同济大学出版社");
session.update(publisher);
}

④删除

/**
* 删除操作,在多对一映射中,无法从1的一端删除,在一对多映射中,可以中1的一端删除记录,
*同时还会强制把n端的外键也删除
*功能:删除出版社,同时引用该记录的外键也删除。
*/
@Test
public void testOneToManyDelete(){
//从n端删除
Books book = (Books) session.get(Books.class, 1);
session.delete(book); //从1端删除,同时n端引用的外键也会被删除
// Publishers publisher = (Publishers) session.get(Publishers.class, 1);
// session.delete(publisher);
}

级联操作需要在1端的映射文件中set节点下,设置级联属性:

cascade(级联)级联的意思是指两个对象之间的操作联运关系,对一个对象执行了操作之后,

对其指定的级联对象也需要执行相同的操作,取值:all,none,save_update,delete。

1.all:代码在所有情况下都执行级联操作

2.none:在所有情况下都不执行级联操作

3.save-update:在保存和更新的情况下执行级联操作

4.delete:在删除的时候执行级联操作

⑤级联添加

/**
* 级联添加
* 需求:添加出版社时,把出版社出版的图书添加到数据表中
*/
@Test
public void testOneToManyCascadeSave(){
//新建出版社对象
Publishers publisher = new Publishers();
publisher.setName("北京大学出版社");
//新建图书对象
Books book = new Books();
book.setTitle("大学英语");
book.setISBN("2018012103");
book.setAuthor("李玲");
book.setWordCount(10000);
book.setUnitPrice(95.5);
book.setContentDescription("无"); //新建图书对象
Books book2 = new Books();
book2.setTitle("管理学");
book2.setISBN("2018012104");
book2.setAuthor("张青");
book2.setWordCount(10000);
book2.setUnitPrice(95.5);
book2.setContentDescription("无"); //设定关联关系,从多的一端维护关系,想要从多端维护关联关系需要在多端配置many-to-one,三条insert语句,推荐使用这种方式
//book.setPublisher(publisher);
//book2.setPublisher(publisher); //设定关联关系,从一的一端维护关系,想要从一端维护关联关系需要在一端配置one-to-many,三条insert语句,两条update语句,不推荐使用这种方式,因为演示1对n,所以使用该方法
publisher.getBks().add(book);
publisher.getBks().add(book2); //设置cascade级联属性之后,可只保存1的一端即可。可省略多的一端的保存操作,反之则不行因为没有多对一映射
session.save(publisher);
//session.save(book);
//session.save(book2); }

⑥级联更新

    /**
* 级联更新
*需求:把id为3的书的出版社改为出版社id为1的出版社
*/ @Test
public void testOneToManyCascadeUpdate(){
//获取id为1的图书对象
Books book = (Books) session.get(Books.class, 3);
//获取id为1的出版社对象
Publishers publisher = (Publishers) session.get(Publishers.class, 1); publisher.getBks().add(book);
//保存出版社对象,三个select,一个update
//session.save(publisher); //保存图书对象,三个select,一个update
session.save(book);
}

⑦级联删除

    /**
* 级联删除
* 需求:删除出版社时,删除该出版社所出版社的图书
*/
@Test
public void testOneToManyCascadeDelete(){
Publishers publisher = (Publishers) session.get(Publishers.class, 4);
//两个select、一个update、三个delete
session.delete(publisher);
}

一对多关联关系

总结:

1端:

①实体类中添加一个集合属性

②映射文件中使用set元素映射数据库字段,并在set节点中配置<one-to-many> 子节点以映射关联关系

③保存操作时,有没有发送多余的update语句在于哪端维护关联关系,而哪端维护关联关系在于是<one-to-many> 还是 <many-to-one>

即推荐使用由n端维护关联关系,使用<many-to-one> 来映射关系,在保存时使用n端实体类中的setter方法

//n端保存1端,订单中设置客户信息
order.setCustomer(customer);
order2.setCustomer(customer);

④级联操作少用

n端:

实体类:普通的JavaBean

映射文件:类属性和数据库字段一一映射即可

Hibernate(7)关联关系_单向1对n的更多相关文章

  1. Hibernate(6)关联关系_单向n对1

    1.单向 n-1 关联只需从 n 的一端可以访问 1 的一端 2.实体类 n端:Order.java public class Order { private Integer orderId; pri ...

  2. 009一对一 主键关联映射_单向(one-to-one)

    009一对一  主键关联映射_单向(one-to-one) ²  两个对象之间是一对一的关系,如Person-IdCard(人—身份证号) ²  有两种策略可以实现一对一的关联映射 主键关联:即让两个 ...

  3. Hibernate —— 映射关联关系

    一.映射多对一关联关系. 1.单向的多对一 (1)以 Customer 和 Order 为例:一个用户可以发出多个订单,而一个订单只能属于一个客户.从 Order 到 Customer 是多对一关联关 ...

  4. Hibernate的关联映射——单向1-N关联

    Hibernate的关联映射--单向1-N关联 单向1-N关联的持久化类里需要使用集合属性.因为1的一端需要访问N的一端,而N的一端将以集合(Set)形式表现.从这个意义上来看,1-N(实际上还包括N ...

  5. Hibernate的关联映射——单向1-1关联

    Hibernate的关联映射--单向1-1关联 对于单向的1-1关联关系,需要在持久化类里增加代表关联实体的成员变量,并为该成员变量添加setter方法和getter方法.从持久化类的代码上看,单向1 ...

  6. Hibernate的关联映射——单向N-1关联

    Hibernate的关联映射--单向N-1关联 N-1是非常常见的关联关系,最常见的父子关系也是N-1关联,单向的N-1关联只需从N的一端可以访问1的一端. 为了让两个持久化类能够支持这种关联映射,程 ...

  7. JPA(六):映射关联关系------映射单向一对多的关联关系

    映射单向一对多的关联关系 新建项目项目请参考<JPA(二):HellWord工程>,基于上一章讲解的<JPA(五):映射关联关系------映射单向多对一的关联关系>中的例子进 ...

  8. hibernate一对一外键单向关联

    关联是类(类的实例)之间的关系,表示有意义和值得关注的连接. 本系列将介绍Hibernate中主要的几种关联映射 Hibernate一对一主键单向关联Hibernate一对一主键双向关联Hiberna ...

  9. hibernate一对一主键单向关联

    关联是类(类的实例)之间的关系,表示有意义和值得关注的连接. 本系列将介绍Hibernate中主要的几种关联映射 Hibernate一对一主键单向关联Hibernate一对一主键双向关联Hiberna ...

随机推荐

  1. 求自然数幂和 B - The Sum of the k-th Powers CodeForces - 622F

    题解: 很多方法 斯特林数推导略麻烦但是不依赖于模数 代码: 拉格朗日插值 由于可以证明这是个K+1次多项式于是可以直接用插值 #include <bits/stdc++.h> using ...

  2. 易企秀H5 json配置文件解密分析

    最近需要参考下易企秀H5的json配置文件,发现已经做了加密,其实前端的加密分析起来只是麻烦点. 抓包分析 先看一个H5: https://h5.eqxiu.com/s/XvEn30op F12可以看 ...

  3. WebApi接口返回值不困惑:返回值类型详解

    前言:已经有一个月没写点什么了,感觉心里空落落的.今天再来篇干货,想要学习Webapi的园友们速速动起来,跟着博主一起来学习吧.作为程序猿,我们都知道参数和返回值是编程领域不可分割的两大块,此前分享了 ...

  4. 【Android】android:windowSoftInputMode属性详解

    activity主窗口与软键盘的交互模式,可以用来避免输入法面板遮挡问题,Android1.5后的一个新特性. 这个属性能影响两件事情: [一]当有焦点产生时,软键盘是隐藏还是显示 [二]是否减少活动 ...

  5. mySql版本的相关问题:com.mysql.cj.jdbc.Driver和com.mysql.jdbc.Driver

    Mysql版本的相关问题:com.mysql.cj.jdbc.Driver和com.mysql.jdbc.Driver 1. 在使用mysql时,控制台日志报错如下: Loading class `c ...

  6. box-shadow阴影 三面显示

    想弄个只显示三面的阴影效果,网上一搜没有解决根本问题,最后还是在css3演示里面找到方法http://www.css88.com/tool/css3Preview/Box-Shadow.html 我把 ...

  7. CentOS 7开机出现welcome to emergency mode! 解决方法

    CentOS7.3昨天用的还好好的的,但是今天开机提示如下(如图提示):welcome to emergency mode!after logging in ,type “journalctl -xb ...

  8. TF之RNN:实现利用scope.reuse_variables()告诉TF想重复利用RNN的参数的案例—Jason niu

    import tensorflow as tf # 22 scope (name_scope/variable_scope) from __future__ import print_function ...

  9. HYSBZ 4034 【树链剖分】+【线段树 】

    <题目链接> 题目大意: 有一棵点数为 N 的树,以点 1 为根,且树点有权值.然后有 M 个 操作,分为三种: 操作 1 :把某个节点 x 的点权增加 a . 操作 2 :把某个节点 x ...

  10. Django分页(二)

    Django分页(二) 要求 .设定每页显示数据条数 # # .用户输入页码(第一页.第二页...) # # .设定显示多少页号 # # .获取当前数据总条数 # # .根据设定显示多少页号和数据总条 ...