zoukankan      html  css  js  c++  java
  • 【SSH 基础】浅谈Hibernate关系映射(3)

    继上篇博客

     

    一对多关联映射(单向)

     

    上面我们介绍了多对一,我们反过来看一对多不就是多对一吗?那还用再进行不同的映射吗?有什么区别吗?一对多和多对一映射原理是一致的,存储是同样的。也就是生成的数据库的表是一样的。他们之间不同的是维护的关系不同。

    他们之间不同点是维护的关系不同

    *多对一维护的关系是:多指向一的关系。有了此关系,载入多的时候能够将一载入上来。

    *一对多维护的关系是:一指向多的关系。有了此关系,在载入一的时候能够将多载入上来。

     

    一个班级有多个学生,通过班级能够看到学生信息。

                        

    Classes的映射关系

    <hibernate-mapping>
    	<class name="com.bjpowernode.hibernate.Classes">
    		<id name="id">
    			<generator class="native"></generator>
    		</id>
    		<property name="name"></property>
    		<set name="students">
    			<key column="classesid"/>
    			<one-to-many class="com.bjpowernode.hibernate.Student"/>
    		</set>
    	</class>
    </hibernate-mapping>
    

    Student的映射关系

    <hibernate-mapping>
    	<class name="com.bjpowernode.hibernate.Student">
    		<id name="id">
    			<generator class="native"></generator>
    		</id>
    		<property name="name"></property>
    	</class>
    
    </hibernate-mapping>

    再看保存的代码:给班级设置学生,而由于学生维护关系。就要在学生端保存班级id--会带来什么问题?

    public void testSave2(){
    		Session session=null;
    		try{
    			session=HibernateUtils.getSession();
    			session.beginTransaction();
    			
    			Student student1=new Student();
    			student1.setName("张三");
    			session.save(student1);
    			
    			Student student2=new Student();
    			student2.setName("李四");
    			//保存学生
    			session.save(student2);
    		
    			Classes classes=new Classes();
    			classes.setName("动力节点");
    			
    			Set students=new HashSet();
    			students.add(student1);
    			students.add(student2);
    			
    			classes.setStudents(students);
    			session.save(classes);
    			session.getTransaction().commit();
    			
    		}catch(Exception e){
    			e.printStackTrace();
    			session.getTransaction().rollback();
    		}finally{
    			HibernateUtils.closeSession(session);
    		}
    	}
    

    在保存数据时,会存在这么一个时刻:so?带来的问题


                                     


    1,从班级能看到学生。是班级来维护关系,不是学生来维护关系,学生不知道自己是哪个班。所以在保存学生的时候,班级id不知道。为了更新学生是哪个班级的要发出非常多update语句来告诉学生是哪个班级的。

    2。当我们设置classesidnot-null=“true”时,则将无法保存数据,解决的方法我们改为双向关联映射。

     

    一对多关联映射(双向)

     

    为了解决一对多单向可能存在的问题,我们採用双向一对多。每一方都能维护对方。

    而不是需求驱动

                   

    一对多双向关联映射方式:

         *在一的一端的集合上採用<key>标签。在多的一端增加一个外键。

         *在多的一端採用<many-to-one>的标签

    !~注意<key>标签和<many-to-one>标签增加字段保持一致,否则会产生数据混乱。

     

    Classes映射文件

    <hibernate-mapping>
    	<class name="com.bjpowernode.hibernate.Classes">
    		<id name="id">
    			<generator class="native"></generator>
    		</id>
    		<property name="name"></property>
    		<set name="students" inverse="true">
    			<key column="classesid"/>
    			<one-to-many class="com.bjpowernode.hibernate.Student"/>
    		</set>
    	</class>	
    </hibernate-mapping>
    

    Student映射文件

    <hibernate-mapping>
    	<class name="com.bjpowernode.hibernate.Student">
    		<id name="id">
    			<generator class="native"></generator>
    		</id>
    		<property name="name"></property>
    		<many-to-one name="classes" column="classesid"></many-to-one>
    	</class>	
    </hibernate-mapping>
    

    注意:Inverse属性

    1、Inverse中文意思为相反的,反转。在hibernate中inverse能够用在一对多和多对多双向关联上,inverse默认是false。为false的时候表示本端能够维护关系,假设inverse为true,则本端不能维护关系。会交给还有一端维护关系。本端失效,所以在一对多关联映射我们通常在多的一端维护关系。让一的一端失效。

    2、Inverse是控制方向上的反转,仅仅影响存储。

     

    比較一对多单向和双向映射,从存储结构上看没有什么差别,可是从配置文件上看。一对多双向关联的配置文件里在多的一端的配置文件上存在<many-to-one>相关配置,即保证多对一的映射。

     

    下篇继续。



  • 相关阅读:
    Cocos2d-x 3.0截屏功能集成
    游戏嵌入Webview网页
    Cocos2dx进阶学习之屏幕适配
    Android如何实现文件下载并自动安装apk包!!!
    LINQ Select变量定义 Expression<Func<TSource, TResult>>
    StringComparison枚举
    .net core DBFirst 生成Model表结构
    .net core反向工程Model生成 配置机密
    axios下载文件.net Core
    EFCore Database-first深入研究
  • 原文地址:https://www.cnblogs.com/yangykaifa/p/7044674.html
Copyright © 2011-2022 走看看