文档章节

Hibernate学习4--Hibernte的映射关系(一)

zimingforever
 zimingforever
发布于 2014/04/18 21:49
字数 1387
阅读 107
收藏 10

Hibernate中最绕的部分莫过于各种映射了,其实大致上就3种,一对一映射onetoone,一对多映射onetomany,多对一映射manytoone,多对多映射manytomany。一对一映射又有一对一主键映射和唯一外键映射。

第一种,一对一主键映射,我们这里用Person和IdCard举例,人和身份证是一对一的关系

其中Idcard的配置如下:

    <class name="com.xiaoming.test.hibernate.personTest.IdCard" table="idcard">
        <id name="id" length="4">
            <generator class="native"></generator>
        </id>
        <property name="cardNo" length="10"></property>
        <one-to-one name="person" ></one-to-one>
    </class>

person的配置如下:

<class name="com.xiaoming.test.hibernate.personTest.Person" table="person">
        <id name="id" length="4">
            <generator class="foreign">
                <param name="property">idCard</param>
            </generator>
        </id>
        <property name="name" length="10"></property>
        <one-to-one name="idCard" constrained="true"></one-to-one>
    </class>

其中person的主键来自idcard,也就是共享idcard的主键。constrained="true"的含义,表明当前主键上存在一个约束,person的主键作为外键参照了idCard,  这里在进行person对象操作时,要求idCard不 能为null 

  IdCard idCard = new IdCard(); 
      idCard.setCardNo("1234567890"); 

      Person person = new Person(); 
      person.setName("张三"); 
      idCard.setPerson(person); 
      session.save(idCard);

这种情况,person是依赖idcard。但是idcard并没有cascade到person,所以这个操作只会保存idcard对象

 IdCard idCard = new IdCard(); 
      idCard.setCardNo("1234567890"); 
      Person person = new Person(); 
      person.setName("张三"); 
      idCard.setPerson(person); 
      session.save(person);

这种情况在保存person的时候,person并没有绑定idcard,而其id又是依赖idcard的id的,所以这样执行会报错。

 IdCard idCard = new IdCard(); 
      idCard.setCardNo("1234567890"); 
      Person person = new Person(); 
      person.setName("张三"); 
      person.setIdCard(idCard); 
      session.save(person);

这种情况是可以正常保存idcard和person的

读取的代码如下:

Person p=(Person)session.load(Person.class, 1); 
      System.out.println(p); 
      System.out.println(p.getIdCard());
        
      IdCard idCard=(IdCard)session.get(IdCard.class, 1); 
      System.out.println(idCard); 
      System.out.println(idCard.getPerson());


第二种映射情况是一对一唯一外键映射, 一对唯一外键关联映射是采用多对一关联映射方法来解决一对一的问题,它就是多对一的一个特例。它是基于这样一种思想:在映射多的一端时采用<many-to-one>标签,并且用属性unique=true来限定它是唯一的,这样就实现了多的一端的多重性为一。但是,它仍保留多対一的痕迹(比如关系模型中增加一个外键字段)。

其中idcard的配置如下:

    <class name="com.xiaoming.test.hibernate.personTest2.IdCard" table="idcard">
        <id name="id" length="4">
            <generator class="native"></generator>
        </id>
        <property name="cardNo" length="10"></property>
        <one-to-one name="person" class="com.xiaoming.test.hibernate.personTest2.Person" property-ref="idCard" cascade="save-update" ></one-to-one>
    </class>

property-ref="idCard"含义,指示加载关联对象时根据关联对象对本对象的引用(即根据person的idCard属性) 测试代码如下:

person的配置如下:

 <class name="com.xiaoming.test.hibernate.personTest2.Person" table="person">
        <id name="id" length="4">
            <generator class="native"></generator>
        </id>
        <property name="name" length="10"></property>
        <!--many-to-one标签的含义,是在本表中增加外键指向另一端。
         unique="true"含义,是本表的本字段加上唯一性约束.
        -->
        <many-to-one name="idCard" class="com.xiaoming.test.hibernate.personTest2.IdCard" unique="true" column="card_id" cascade="save-update"></many-to-one>
    </class>

many-to-one是在本表中增加外键指向另一端,unique=true的含义表示在本表的本字段加上唯一性约束。


 IdCard idCard=new IdCard(); 
      idCard.setCardNo("1234567890"); 
        
      Person person=new Person(); 
      person.setIdCard(idCard); 
      session.save(person);

这种情况是ok的,会同事插入person和idcard两个对象,因为idcard中的onetoone标签有cacade=save-updatre属性

IdCard idCard=new IdCard(); 
      idCard.setCardNo("1234567890"); 
      session.save(idCard); 
        
      Person person=new Person(); 
      person.setName("张三"); 
      person.setIdCard(idCard); 

      session.save(person);

 这种写法也是对的。会同时插入idcard及person属性

 Person person=new Person(); 
      person.setName("奇隆"); 
        
      IdCard idCard=new IdCard(); 
      idCard.setCardNo("1234567890"); 
      idCard.setPerson(person);

如果在IdCard一端没有cascade="save-update",显然这里会只插入idCard,而不会级联插入它的person属性 。如果在IdCard一端有cascade="save-update",则在插入idCard后,会再插入person,但是idCard_id字段会是null,而不会把person的idCard_id更新. 所以像这种情况,应该在"多"的一端插入并级联"一"的一端.

读取操作如下:

  Person p=(Person)session.load(Person.class, 2); 
      System.out.println(p); 
      System.out.println(p.getIdCard()); 
      
      IdCard idCard=(IdCard)session.get(IdCard.class, 5); 
      System.out.println(idCard); 
      System.out.println(idCard.getPerson());

第3中是多对一的映射,我们这里用group和user来举例

Group配置对下:

    <class name="com.xiaoming.test.hibernate.userTest.Group" table="group1">
        <id name="id" length="4">
            <generator class="native"></generator>
        </id>
        <property name="name" length="10"></property>
    </class>

User的配置如下:

 <class name="com.xiaoming.test.hibernate.userTest.User" table="user1">
        <id name="id" length="4">
            <generator class="native"></generator>
        </id>
        <property name="name" length="10"></property>
        <many-to-one name="group" column="group_id" cascade="save-update"></many-to-one>
    </class>

many-to-one含义,会在多的一端加入一个外键指向一的一端,以供加载时使用.外键由column属性指定,默认和实体属性名相同. cascade操作本对象时级联操作它的关联对象

测试方法如下:

 Group group = new Group();
        group.setName("研发组"); 
        User user=new User(); 
        user.setName("奇隆"); 
        user.setGroup(group); 
        session.save(user);

这种操作是ok的,因为user加了casecade属性,所以在插入user之前会插入group

Group group=(Group)session.get(Group.class, 2); 
        User user=new User();     
        user.setName("谢霆锋"); 
        user.setGroup(group); 
        session.save(user);*/

这种情况group是已经在数据库中并加载出来的,所以也能保存成功。

  User user = (User) session.get(User.class, 3);// 只是加载了user对象和它所在组的对象group的id属性,并没有加载group对象 
      System.out.println(user); 
      System.out.println(user.getGroup()); 
      session.save(user); 
      user.setName("郑伊健"); 
      session.save(user);

第一次save的时候由于user没有做update操作,所以不会触发update操作,第二个save操作由于user有变动,所以可以触发update操作

其实每种案例都差不多,无非就是one和many标签及其中属性的配合,另外java代码中注意调用的顺序,就可以正常操作对应的对象属性,这一次这几种映射关系没有介绍完,下一次再学习manytoone,manytomany及符合主键的映射。



© 著作权归作者所有

zimingforever
粉丝 142
博文 266
码字总数 315040
作品 0
杭州
程序员
私信 提问
Hibernate学习4--Hibernte的映射关系(二)

上一节我们主要研究下了Hibernate中的一一映射和多对一映射,这节我们看下Hibernate中的其他几种映射,包括一对多映射,多对多映射,复合主键映射及继承映射。 第一种是一对多映射,“一对多...

王小明123
2014/04/20
89
0
Hibernate学习1--SpringMVC+Hibernate集成环境搭建

除了刚毕业那会用了几个月的hibernate好像好久都没有碰过了,正好最近在整理以前的学习笔记就把这块知识系统的学习一下,特别是hibernate和ibatis的对比应该对我现在做的东西有很大的帮助。 ...

王小明123
2014/04/03
2.7K
0
Hibernate学习3--Hibernte的映射关系(基础概念篇)

前两节我们分别从Hibernate的demo和Hibernate的概念上熟悉了Hibernate的使用,这一节我们来了解Hibernate中的映射关系 首先我们了解下Hibernate映射文件中的各种标签的用法 1<hibernate-mapp...

王小明123
2014/04/14
368
0
iBatis和Hibernate浅析

iBatis和Hibernate浅析 Hibernate Hibernate是一个开放源代码的对象关系映射框架,它对JDBC进行了非常轻量级的对象封装,使得Java程序员可以随心所欲的使用对象编程思维来操纵数据库。Hiber...

JAVA__
2012/08/16
158
1
IBatis和Hibernate区别

原文出处:http://www.cnblogs.com/mingyongcheng/p/3588100.html IBatis和Hibernate区别 1. 简介 Hibernate是当前最流行的O/R mapping框架。它出身于sf.net,现在已经成为Jboss的一部分了。...

ponpon_
2014/06/26
0
0

没有更多内容

加载失败,请刷新页面

加载更多

IT兄弟连 HTML5教程 介绍HTML5给你认识 习题

1.关于HTML5说法正确的是:(C) A.HTML5只是对HTML4的一个简单升级 B.所有主流浏览器都支持HTML5 C.HTML5新增了离线缓存机制 D.HTML5主要是针对移动端进行了优化 2.为了标识一个HTML文...

老码农的一亩三分地
7分钟前
2
0
关于1加手机rom的分析过程

1、关于清理app缓存的信息 framework.jar和services.jar文件,都位于/system/framework目录下面 framework.jar的android.os.Intent类里面定义了action "android.intent.action.CLEAR_PKG",这......

shatian
8分钟前
1
0
[docker]使用root进入docker

docker exec -it --user root ed0 /bin/bash https://blog.csdn.net/kaifeng86/article/details/73237056...

Danni3
21分钟前
2
0
通过重编译icu替换icuxxxx.dll减少QT5发布体积

最近需要使用QT写一个程序,选择了比较新的QT5.3以获得更多特性进行快速开发。但是QTCreator编译出来的程序是动态链接版本,接着就头痛了,自己程序很小,但是所需要携带的动态链接库却很大,...

shzwork
23分钟前
3
0
关于二叉树的前序、中序、后序三种遍历

二叉树遍历分为三种:前序、中序、后序,其中序遍历最为重要。为啥叫这个名字?是根据根节点的顺序命名的。 比如上图正常的一个满节点,A:根节点、B:左节点、C:右节点,前序顺序是ABC(根...

城市之雾
28分钟前
5
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部