Hibernate 关联映射
------------------------------------------------
hibernate多对一关联映射
关联映射的本质:
将关联关系映射到数据库表,关联关系在对象模型中体现为一个或多个引用
<many-to-one>会在多的一端添加一个外键,指向一的一端,这个外键是由<many-to-one>
中的column属性定义的,如果忽略这个属性,默认外键与实体类的属性一致注意:如果实体类的名称和属性与sql的关键字重复,必须重新命名
<many-to-one>标签定义示例:
*<many-to-onename="group"column="groupid"/>
理解级联的含义?
对象之间的连锁操作
------------------------------------------hibernate一对一主键关联映射(单向关联Person---->IdCard)
一对一主键关联映射:让两个实体对象的id保持相同,这样可以避免多余的字段被创建
具体映射方式:
<classname="com.bjsxt.hibernate.Person"table="t_person">
<idname="id">
<!--person的主键来源于IdCard,共享IdCard的主键-->
<generatorclass="foreign">
<paramname="property">idCard</param>
</generator>
</id>
<propertyname="name"/>
<!--one-to-one标签指示hibernate如何加载其引用对象,默认根据主键加载
constrained="true"表明当前主键上存在一个约束,person的主键作为外键参照了IdCard
-->
<one-to-onename="idCard"constrained="true"/>
</class>-------------------------------------------------------
hibernate一对一主键关联映射(双向关联Person<---->IdCard)
需要在IdCard中加入<one-to-one>标签指向person,指示hibernate如何加载person默认根据主键加载
------------------------------------------
hibernate一对一唯一外键关联映射(单向关联Person---->IdCard)
一对一唯一外键关联映射实际上就是多对一关联映射的特例
可以采用<many-to-one>标签,指定多的一端的unique=true,则限制了多的一端的多重性为一通过这种手段来映射一对一唯一外键关联
----------------------------------------
hibernate一对一唯一外键关联映射(双向关联Person<---->IdCard)
一对一唯一外键双向关联映射,需要在另一端(IdCard),添加<one-to-one>标签,指示hibernate如何
加载其引用对象,默认情况下根据主键加载Person,因为外键关联映射中,因为外键关联映射中两个实体的关系
是通过person中的idCard维护的,所以不能根据person的主键来加载,而是根据person的外键来加载person
对象,如:
<one-to-one name="person" property-ref="idCard"/>-----------------------------------------------session.flush测试
session.flush主要做两件事:
*清理缓存(脏数据对比)
* 执行sqlhibernate中sql的执行顺序: hibernate按照save(insert)、update和delete顺序提交相关操作
set transaction isolation level read uncommited
-----------------------------------------------080701
hibernate一对多关联映射(单向关联)
这个映射的本质:采用了多对一映射原理
多对一关联映射:在多的一端加入一个外键,指向一的一端,它维护的是多到一的关系一对多关联映射:在多的一端加入一个外键,指向一的一端,它维护的是一到多的关系
也就是说一对多和多对一映射策略是一致的,只是站的角度不同
一对多关联映射让hibernate在一的一端维护关系存在缺点:
*会发出多余的update语句,建立班级和学生之间的关系,影响性能
* 如果student表中的classesid设置为非空,将无法保存数据--------------------
hibernate一对多关联映射(双向关联)
一对多双向关联映射:
*在一一端的集合上使用<key>,在对方表中加入一个外键指向一一端
*在多一端采用<many-to-one>
注意:<key>标签指定的外键字段必须和<many-to-one>指定的外键字段一致,否则引用字段的错误
如果在”一“一端维护一对多关联关系,hibernate会发出多余的udpate语句,所以我们一般在多
的一端来维护关联关系关于inverse属性:
inverse主要用在一对多和多对多双向关联上,inverse可以被设置到集合标签<set>上,
默认inverse为false,所以我们可以从”一“一端和”多“一端维护关联关系,
如果设置成inverse为true,则我们只能从多一端来维护关联关系
注意:inverse属性,只影响数据的存储,也就是持久化
inverse和cascade
*inverse是关联关系的控制方向
*cascade操作上的连锁反应
------------------------------hibernate多对多关联映射(单向关联)
映射方法:
<set name="roles" table="t_user_role">
<keycolumn="userid"/>
<many-to-manyclass="com.bjsxt.hibernate.Role"column="roleid"/>
</set>
-----------------------------------------hibernate多对多关联映射(双向关联)
映射方法:
<setname="roles"table="t_user_role">
<keycolumn="userid"/>
<many-to-manyclass="com.bjsxt.hibernate.Role"column="roleid"/>
</set>
table属性值必须和单向关联中的table属性值一致
<key>中column属性值要与单向关联中的<many-to-many>标签中的column属性值一致
在<many-to-many>中的column属性值要与单向关联中<key>标签的column属性值一致
------------------------------------------------------lazy策略可以应用在:
*<class>标签上,可以取值true/false
*<property>标签上,可以取值true/false,需要类增强工具
*<set><list>集合标签上,可以取值true/false/extra
*<one-to-one>、<many-to-one>单端关联上,可以取值false/proxy/noproxy
lazy的概念:在正真使用的时候发出查询语句加载相应的对象hibernate支持lazy策略只有在session打开状态下才有效
hibernate类级别的lazy只对普通属性起作用,可以控制什么时候加载这些普通属性
---------------------------------hibernate在集合上的lazy策略:可以取值true/false/extra
true:默认取值,它的意思是只有在调用这个集合获取里面的元素对象时,才发出查询语句,加载其
集合元素的数据
false:取消lazy特性,即在加载对象的同时,就发出第二条查询语句加载其关联集合的数据
extra:一种比较聪明的lazy策略,即调用集合的size等方法的时候,hibernate并不会去
加载整个集合的数据,而是发出一条聪明的SQL语句,以便获得需要的值,只有在真正需
要用到这些集合元素对象数据的时候,才去发出查询语句加载所有对象的数据<class>标签上配置的lazy不会影响到集合上的lazy特性
-----------------------------------------------
hibernate在单端关联上的lazy策略可以取值:false/proxy/noproxy
false:取消lazy策略,即在加载对象的同时,发出查询语句,加载其关联对象
proxy:这是hibernate对单端关联的默认lazy策略,即只有在调用到其关联对象的方法的时候
才真正发出查询语句查询其对象数据,其关联对象是代理类
no-proxy:这种lazy特性需要对类进行增强,使用no-proxy,其关联对象不是代理类<class>标签上配置的lazy不会影响到单端关联对象上的lazy特性