(十二)Hibernate中的多表操作(2):单向多对一
- 由“多”方可知“一”方的信息,比如多个员工使用同一栋公寓,员工可以知道公寓的信息,而公寓无法知道员工的信息。
案例一:使用xml配置
- pojo类 Group.java
package bean; // default package /**
* Group entity. @author MyEclipse Persistence Tools
*/ public class Group implements java.io.Serializable { // Fields private Integer groupid;
private String groupname; //省略get和set方法
//省略空的和满的构造方法 }
GroupUser.java
package bean; // default package /**
* GroupUser entity. @author MyEclipse Persistence Tools
*/ public class GroupUser implements java.io.Serializable { // Fields private Integer userid;
private String username; private Group group; //省略get和set方法
//省略构造方法 }
- 实体映射文件 Group.hbm.xml
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd"> <hibernate-mapping>
<class name="bean.Group" table="t_group" catalog="test">
<id name="groupid" type="java.lang.Integer">
<column name="groupid" />
<generator class="assigned"></generator>
</id>
<property name="groupname" type="java.lang.String">
<column name="groupname" />
</property>
</class>
</hibernate-mapping>
GroupUser.hbm.xml
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd">
<!--
Mapping file autogenerated by MyEclipse Persistence Tools
-->
<hibernate-mapping>
<class name="bean.GroupUser" table="t_groupuser" catalog="test">
<id name="userid" type="java.lang.Integer">
<column name="userid" />
<generator class="assigned"></generator>
</id>
<property name="username" type="java.lang.String">
<column name="username" />
</property>
<!-- name的值要与本类的属性名一致,这里指定这个bean映射的表的外键为group_id属性且该属性是自动生成的,所以必须与数据库中的外键字段一致,
//所以该bean就不需要设置表中外键的映射了。
// hibernate默认该外键关联group映射的表的主键, -->
<many-to-one name="group" class="bean.Group" column="group_id" cascade="all"></many-to-one> <!-- class值指定了“一”方的类 -->
</class>
</hibernate-mapping>
<many-to-one >元素建立了department属性和employee表的外键depart_id之间的映射.
<many-to-one name="group" class="bean.Group" column="group_id" cascade="all">
- <many-to-one name="group" class="bean.Group" column="group_id" cascade="all">这种情况,hibernate会默认去group对象中查找主键值,因为hibernate默认的是外键对应另一个表中的主键的,如果想对应group中的其它属性,如”name”,则可以使用<many-to-one name=”group” column=”group_id” property-ref=”name”/>
name: 设定待映射的持久化类的属性名,此外为employee类的department属性.
column: 设定和持久化类的属性对应的表的外键,此外为employee表的外键depart_id.
class(可选):设定持久化类的属性的类型,此处设定department的类型是Department类.
not-null(可选):如果为true,表示department属性不能为null,该属性的默认值为false.当为true时,生成的employee表中depart_id外键会设置not-null约束,所以当Hibernate保存Employee对象时,会先检查它的department属性是否为null,如果为null,则会抛出异常.
案例二:使用注解配置
- 多个用户对应一个组,一个组有多个用户。且多个用户可以知道组的信息,但是组不能知道用户的信息。
- 数据库中表结构:
- 建议pojo持久化类: Group.java
package bean; import java.io.Serializable; import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.Table; import org.hibernate.annotations.GenericGenerator; @Entity
@Table(name = "t_group")
public class Group implements Serializable { @Id
@GeneratedValue(generator="a")
@GenericGenerator(name="a",strategy="assigned")
private Integer groupid;
@Column(name="groupname")
private String groupName; //省略get和set方法
//省略空的构造方法和满构造方法 }
- GroupUser.java
package bean; import java.io.Serializable; import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.Table; import org.hibernate.annotations.GenericGenerator; @Entity
@Table(name = "t_groupuser")
public class GroupUser implements Serializable { @Id
@GeneratedValue(generator = "designed")
@GenericGenerator(name = "designed", strategy = "assigned")
private Integer userid; private String username; @ManyToOne(cascade = { CascadeType.REMOVE, CascadeType.MERGE }) // 设置关联关系和级联类型
@JoinColumn(name = "group_id") // 该注解表示指定外键,这里指定这个bean映射的表的外键为group_id属性且该属性是自动生成的,所以必须与数据库中的外键字段一致,所以该bean就不需要设置表中外键的映射了。
// hibernate默认该外键关联group映射的表的主键, private Group group; public GroupUser() { } public GroupUser(Integer userid, String username) {
super();
this.userid = userid;
this.username = username; } public Integer getUserid() {
return userid;
} public void setUserid(Integer userid) {
this.userid = userid;
} public String getUsername() {
return username;
} public void setUsername(String username) {
this.username = username;
} public Group getGroup() {
return group;
} public void setGroup(Group group) {
this.group = group;
} }
- 测试类 Test_ManytoOne.java
package action; import org.hibernate.Session;
import org.hibernate.Transaction; import bean.Group;
import bean.GroupUser;
import util.HibernateUtil; /**
* 本类测试多对一的操作
* @author 半颗柠檬、
*
*/
public class Test_ManytoOne {
public static void main(String[] args) {
Test_ManytoOne.save(); // Test_ManytoOne.select(); // Test_ManytoOne.delete();
} public static void save(){
Session session = null;
Transaction tran = null;
try {
session = HibernateUtil.getSessionFactory().getCurrentSession();
tran=session.beginTransaction(); //添加一个组
Group group=new Group();
group.setGid(1);
group.setGroupName("管理员组"); //添加组成员
GroupUser user=new GroupUser();
user.setUserid(1);
user.setUsername("admin1");
user.setGroup(group); GroupUser user1=new GroupUser();
user1.setUserid(2);
user1.setUsername("admin2");
user1.setGroup(group); session.save(group);
session.save(user);
session.save(user1); tran.commit();
} catch (Exception e) {
e.printStackTrace();
tran.rollback();
}
} /**
* 测试单向对一是否只能多方读取一方,而一方不能读取多方
*/
private static void select() {
Session session = null;
Transaction tran = null;
try {
session = HibernateUtil.getSessionFactory().getCurrentSession();
tran=session.beginTransaction(); GroupUser user= (GroupUser)session.get(GroupUser.class, new Integer(2));
System.out.println(user.getUserid()+"\t"+user.getUsername()); //单向获取“一”方的信息 Group group=user.getGroup();
System.out.println("groupid="+group.getGid()+"\t"+group.getGroupName()); tran.commit();
} catch (Exception e) {
e.printStackTrace();
tran.rollback();
}
} /**
* 删除Many一方时,默认不会级联删除One的一方。
*
* 如果要级联删除:,一般使用代码手动级联更新
*
* A:使用代码来控制级联删除。[使用这种方式]
*
* B:配置级联关系,让Hibernate自动执行。
*
* 在关联关系中配置cascade属性。
*
* @ManyToOne(cascade = { CascadeType.REMOVE, CascadeType.MERGE })
*
*/
private static void delete() {
Session session = null;
Transaction tx = null;
try {
session = HibernateUtil.getSession();
tx = session.beginTransaction();
/**
* A:使用代码控制级联
*/
// GroupUser user = (GroupUser) session.get(GroupUser.class,
// new Integer(1));
//
// session.delete(user);
//
// Group group = user.getGroup();
// session.delete(group);
/**
* B 在关联关系中配置cascade属性之后
*/
GroupUser user = (GroupUser) session.get(GroupUser.class,
new Integer(1));
session.delete(user); tx.commit();
} catch (Exception e) {
e.printStackTrace();
tx.rollback();
} finally {
HibernateUtil.closeSession();
}
} }
- 一对多可以从“一”方得到“多”方的信息,那么可以用
OneToMany
@JoinColumn(name = " ")
@OrderBy(value=" studentID desc")
来对获得的“多”方信息进行排序
(十二)Hibernate中的多表操作(2):单向多对一的更多相关文章
- (转)Hibernate中的多表操作
http://blog.csdn.net/yerenyuan_pku/article/details/70556208 Hibernate中的多表操作 在实际开发中,我们不可能只是简简单单地去操作单表 ...
- (十五)Hibernate中的多表操作(5):双向多对多
Hibernate的双向关联. 对象之间可以相互读取. 双向只针对读取的操作.对于增.删除.改的操作没有任何影响. 案例 : 实现双向多对多 MenuBean.java package ...
- (十三)Hibernate中的多表操作(3):单向多对多
多对多的处理方式是,有一张中间表,中间表保存两个多方之间的关系.首先来看实际应用场景:在之前开发的系统中,应用了基于角色的控制访问,也就是RBAC模型,一个用户可能存在多种角色,一种角色也可能有多个用 ...
- (十四)Hibernate中的多表操作(4):单向一对一
案例一: 注解方式实现一对一 UserBean.java package bean; import java.io.Serializable; import javax.persistence.Col ...
- (十一)Hibernate中的多表操作(1):单向一对多
一.单向一对多() 案例一(用XML文件配置): 一个班级有多个学生,班级可以查看所有学生的信息. ClassBean.java package bean; import java.util.Hash ...
- J2EE进阶(十六)Hibernate 中getHibernateTemplate()方法使用
J2EE进阶(十六)Hibernate 中getHibernateTemplate()方法使用 spring 中获得由spring所配置的hibernate的操作对象,然后利用此对象进行,保存,修 ...
- 二十二、OGNL的一些其他操作
二十二.OGNL的一些其他操作 投影 ?判断满足条件 动作类代码: ^ $ public class Demo2Action extends ActionSupport { public ...
- 第二十二章 Django会话与表单验证
第二十二章 Django会话与表单验证 第一课 模板回顾 1.基本操作 def func(req): return render(req,'index.html',{'val':[1,2,3...]} ...
- (转)SpringMVC学习(十二)——SpringMVC中的拦截器
http://blog.csdn.net/yerenyuan_pku/article/details/72567761 SpringMVC的处理器拦截器类似于Servlet开发中的过滤器Filter, ...
随机推荐
- Thingsboard学习之二安装Docker和Docker-Compose
安装系统更新系统,参考<Thingsboard学习之一CentOS安装系统更新> 尝试更新系统 yum update 增加一个用户并设置密码,并将用户增加到管理员 # 添加用户(可选) s ...
- 详谈mysqldump数据导出的问题
1,使用mysqldump时报错(1064),这个是因为mysqldump版本太低与当前数据库版本不一致导致的. mysqldump: Couldn't execute 'SET OPTION SQL ...
- Mybatis xml mapper 特殊写法总结
项目告一段落,业务代码也写得差不多了,框架仍然用的是 ssm ,为了省去单表数据库操作的代码编写,继续用 mybatis generator 生成单表对应的实体类.dao层映射关联及配置文件,私下还尝 ...
- python socketpool:通用连接池
简介 在软件开发中经常要管理各种“连接”资源,通常我们会使用对应的连接池来管理,比如mysql数据库连接可以用sqlalchemy中的池来管理,thrift连接可以通过thriftpool管理,red ...
- linux工程管理软件—make
一.make概述 make是一种代码维护工具make工具会根据makefile文件定义的规则和步骤,完成整个软件项目的代码维护工作.一般用来简化编译工作,可以极大地提高软件开发的效率. win ...
- OpenJudge计算概论-找和为K的两个元素
/*============================================================== 找和为K的两个元素 总时间限制: 1000ms 内存限制: 65536 ...
- <javaScript>document.body为null的问题
虽然body是JS中的DOM技术中所有浏览器支持的属性,但在我们的代码编写中,还是会碰到document.is null问题 例如:我们可以使用alert(document.body);的时候,就会提 ...
- react图片自适应组件
import * as React from 'react'; import 'animate.css/animate.css' import {AutoImg} from "./style ...
- 利用redis实现分布式事务锁,解决高并发环境下库存扣减
利用redis实现分布式事务锁,解决高并发环境下库存扣减 问题描述: 某电商平台,首发一款新品手机,每人限购2台,预计会有10W的并发,在该情况下,如果扣减库存,保证不会超卖 解决方案一 利用数据 ...
- 让群辉支持DTS音轨
让群晖Video Station支持DTS音轨的方法原因:因版权问题,群晖Video Station默认不支持DTS音轨,因此默认不能播放使用DTS音轨的影片. 网上搜到好多解决办法,通常是让添加源h ...