zoukankan      html  css  js  c++  java
  • Hibernate(五)——经典解析一对一关联映射

    前面两篇介绍了多对一、一对多的映射。今天分享下一对一的关联映射关系。有两种策略可以实现一对一的关联映射:主键关联、唯一外键关联。


    主键关联——两个表有完全相同的主键值,来表示它们的一对一的关系。数据库中没有额外的字段去维护它们之间的关系,就只是靠着主键来维持关系。


    唯一外键关联——增加一个额外的字段,维护他们之间的一对一关系。


    现在要用一对一来描述人和身份证的关系。每个人只有一个身份证。


    1、单向主键关联进行描述



    根据上图,我们需要在person端进行如下配置:

    <?xml version="1.0"?>
    <!DOCTYPE hibernate-mapping PUBLIC 
    	"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
    	"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
    <hibernate-mapping>
    	<class name="com.lzq.hibernate.Person" table="t_person">
    		<id name="id">
    		<!--采用foreign生成策略,foreign会取得关联对象的标识-->
    			<generator class="foreign">
    				<!--property只关联对象-->
    				<param name="property">idCard</param>
    			</generator>
    		</id>
    		<property name="name" />
    		<!-- 
    			one-to-one指示hibernate如何加载其关联对象,默认根据主键加载
    			也就是拿到关系字段值,根据对端的主键来加载关联对象
    		 -->
    		<one-to-one name="idCard" constrained="true"></one-to-one>
    	</class>
    </hibernate-mapping>

    主键生成策略使用foreign,它能够取得关联对象的标识。上面代码中“constrained='true'”表示当前主键(person的主键)还是一个外键,参照了对端的主键(IdCard的主键),也就是会生成外键约束语句。


    2、单向唯一外键关联

    根据上图,我们需要对Person进行如下配置:

    <?xml version="1.0"?>
    <!DOCTYPE hibernate-mapping PUBLIC 
    	"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
    	"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
    <hibernate-mapping>
    	<class name="com.lzq.hibernate.Person" table="t_person">
    		<id name="id">
    			<generator class="native" />
    		</id>
    		<property name="name" />
                    <!-- 用多对一的配置+唯一的限制,来表示一对一的关联关系-->
                    <many-to-one name="idCard" unique="true" />
    	</class>
    </hibernate-mapping>


    唯一外键关联的主键生成策略不像主键关联那样必须使用foreign外键生成策略,这里采用的是native。另外一对一的关系采用多对一的配置+唯一的限制,来表示一对一的关联关系。


    3、双向主键关联进行描述

    该种情况,我们仍然在Person端维护关系字段,而且不能够在IdCard再维护关系。如果在IdCard端也维护关系,两段都维护主键,那么就会产生混乱。所以,此处的双向,我们单只加载的时候,也可以从IdCard方加载上来。




    在双向关系中,还需要将关系配置在IdCard中,对IdCard进行如下配置:


    <?xml version="1.0"?>
    <!DOCTYPE hibernate-mapping PUBLIC 
    	"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
    	"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
    <hibernate-mapping>
    	<class name="com.lzq.hibernate.IdCard" table="t_id_card">
    		<id name="id">
    			<generator class="native" />
    		</id>
    		<property name="cardNo" />
    		<!-- 这是默认情况:由于抓去策略不同,只显示一条sql语句
    		 <one-to-one name="person" fetch="join"></one-to-one>
    		 -->
    		 <!--
    		 	由于抓去策略不同,显示两条sql语句:
    		 	第一条查询身份证,第二条查询人
    		  -->
    		 <one-to-one name="person" fetch="select"></one-to-one>
    	</class>
    </hibernate-mapping>


    双向一对一主键关联映射需要在IdCard加入<one-to-one>标签,指是hibernate将关联对象Person根据主键加载上来。


    4、双向唯一外键关联描述

    此处的双向同上面提到的双向的概念一致,关系还是只是Person端维护,这里双向只是指从IdCard端能够加载上来。


    IdCard端关系:

    <?xml version="1.0"?>
    <!DOCTYPE hibernate-mapping PUBLIC 
    	"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
    	"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
    <hibernate-mapping>
    	<class name="com.lzq.hibernate.IdCard" table="t_id_card">
    		<id name="id">
    			<generator class="native" />
    		</id>
    		<property name="cardNo" />
    		 <one-to-one name="person" property-ref="idCard"></one-to-one>
    	</class>
    </hibernate-mapping>


    一对一双向外键关联采用<one-to-one>标签映射,必须执行该标签中的property-ref属性为关系字段的名称。


    一对一的关联映射,经常使用的还是单向唯一外键关联。主键关联的方式扩展性不好,而且不太灵活。两种方式的区别在文章开头也有提到,映射方式肯定是不同的,另外在数据库表也有不同,主键关联的方式不会使用额外的字段来维护关系,而唯一外键关联方式需要在一端使用额外的字段维护关系。


  • 相关阅读:
    互联网、云大数据相关书籍推荐
    育儿、教育书籍推荐
    MySQL客户端工具的选择
    解决Windows10或者其他版本Windows Update报错的问题
    启动Myeclipse报错“Failed to create the Java Virtual Machine”的解决办法
    mysql的日期存储字段比较int,datetime,timestamp区别
    nginx增加ssl服务方法
    mysql导入出现MySQL Error 1153
    mysql忘记密码修改方法
    清空本地ssh记录数据,ssh: connect to host Ip port 22: Connection refused
  • 原文地址:https://www.cnblogs.com/javawebsoa/p/3177753.html
Copyright © 2011-2022 走看看