zoukankan      html  css  js  c++  java
  • 映射:一对多(部门对员工)和多对一(员工对部门)

    package dao.po;  
    import java.util.Set;  
    //部门类
    public class Department{  
        private int id;//部门的ID   
        private String name;//部门的名称  
        private Set<Employee> emps;//部门下的所有员工 (一对多关系)  
    }
    package dao.po;  
    //员工类   
    public class Employee{  
        private int id;// 员工的ID   
        private String name;// 员工的名称  
        private Department depart;//员工所在部门 (是多对一关系)  
    }  

      XML:

    <?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 package="dao.po">  
        <class name="Department">       
            <id name="id">  
                <generator class="native"/>  
            </id>       
            <property name="name" not-null="true" length="255" column="name"/>  
            <set name="emps">     <!-- emps 是Department的一个属性 -->      
                <key column="depart_id"></key>  <!-- 通过员工表的 depart_id字段来关联,它是字段名 -->  
                <one-to-many class="Employee"/>   <!-- emps的类型是Employee -->  
            </set>  
        </class>   
    </hibernate-mapping>  

    下面是重点:

       <set name="emps">        <!-- emps 是Department的一个属性 -->    
                <key column="depart_id"></key>    <!-- 通过员工表的 depart_id字段来关联,它是字段名 -->
                <one-to-many class="Employee"/>    <!-- emps的类型是Employee -->
            </set>

    <?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 package="dao.po">
        <class name="Employee">         
            <id name="id">  
                <generator class="native"/>  
            </id>       
            <property name="name" not-null="true" length="255" column="`name`"/>  
            <!-- 这里做多对一映射    -->  
            <!-- name="depart"是Employee类的属性名 -->  
            <!-- column="depart_id" 是表中字段名 -->  
            <many-to-one name="depart" column="depart_id" not-null="true"></many-to-one>  
        </class>
    </hibernate-mapping>  

    一对多 (一个部门 对 多个员工):查询部门(部门下有员工)

    public static void main(final String[] args){  
        final Department de = query(2);  
        final Set<Employee> set = de.getEmps(); //本部门的所有员工  
        for (final Employee em : set){  
            System.out.println(em.getName());  
        }
    }
    /** 
     * 查询部门(部门下有员工) 
     * @param id  部门ID 
     * @return 部门对象 
     */  
    public static Department query(final int id){  
        Session session = null;  
        try{  
            session = HibernateUtil.getSeesion();  
            final Transaction tx = session.beginTransaction();  
            final Department de = (Department) session.get(Department.class, id); //按ID查      
            //因为 部门的 "员工" 属性会懒加载,  
            //在session关闭后,调用de.getEmps()无法取到员工信息  
            //所以这里用 Hibernate.initialize(de.getEmps()) 提前加载一下.            
            Hibernate.initialize(de.getEmps());  
            tx.commit();  
            return de;  
        }finally{  
            if (session != null){  
                session.close();  
            }  
        }
    }

    二、多对一(员工对部门)

    package dao.po;  
    // 员工类
    public class Employee  {  
        private int id; // 员工的ID   
        private String name; // 员工的名称  
        private Department depart;    //员工所在部门, 是多对一关系  
    }  
    package dao.po;  
    //部门类 
    public class Department  {  
        private int id; //部门的ID   
        private String name;   //部门的名称  
    }
    <?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  package="dao.po">  
        <class name="Employee">     
            <id name="id">  
                <generator class="native"/>  
            </id>  
            <property name="name" not-null="true" length="255" column="`name`"/>  
            <!-- 这里做多对一映射    -->  
            <!-- name="depart"是Employee类的属性名 -->  
            <!-- column="depart_id" 是表中字段名 -->  
            <!-- 注意:下面没有非空 约束 , 很多情况,外键是有非空约束的, 一会后面说-->  
            <!--column="depart_id" 中的depart_id是Employee对象的depart属性映射为Employee表中的depart_id字段-->  
            <many-to-one name="depart" column="depart_id" ></many-to-one>  
        </class>  
    </hibernate-mapping>  
    <?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  package="dao.po">  
        <class name="Department">   
            <id name="id">  
                <generator class="native"/>  
            </id>       
            <property name="name" not-null="true" length="255" column="`name`"/> 
    </class>  
    </hibernate-mapping>  

      保存员工 和 部门:

    package dao;  
    import org.hibernate.Session;  
    import org.hibernate.Transaction;  
    import dao.po.Department;  
    import dao.po.Employee;  
    //多对一的例子 , 多个员工 对 一个部门 
    public class Many2One{  
        public static void main(final String[] args){  
            add(); //添加两个员工, 一个部门  
        }  
        //添加两个员工, 一个部门 
        public static void add(){  
            final Department depart = new Department(); //部门  
            depart.setName("技术部");  
            final Employee em1 = new Employee(); //员工 一  
            em1.setName("赵磊");  
            em1.setDepart(depart);  
            final Employee em2 = new Employee(); //员工 二  
            em2.setName("陈加俊");  
            em2.setDepart(depart);  
            Session session = null;  
            try{  
                session = HibernateUtil.getSeesion();  
                final Transaction tx = session.beginTransaction();  
                session.save(depart); //先插入部门  
                session.save(em1); //后插入员工, 因为员工的外键是 部门  
                session.save(em2);  
                tx.commit();  
            }finally{  
                if (session != null){  
                    session.close();
                }  
            }  
        }  
    }  

      注意:保存的顺序:

      第一种:

                session.save(depart); //先插入部门
                session.save(em1); //后插入员工, 因为员工的外键是 部门
                session.save(em2);

      输出的SQL:

                Hibernate: insert into Department (`name`) values (?)
                Hibernate: insert into Employee (`name`, depart_id) values (?, ?)
                Hibernate: insert into Employee (`name`, depart_id) values (?, ?)

      第二种:

                session.save(em1); //先插入员工
                session.save(em2);
                session.save(depart); //后插入部门

      输出的SQL:

                Hibernate: insert into Employee (`name`, depart_id) values (?, ?)
                Hibernate: insert into Employee (`name`, depart_id) values (?, ?)
                Hibernate: insert into Department (`name`) values (?)
                Hibernate: update Employee set `name`=?, depart_id=? where id=?
                Hibernate: update Employee set `name`=?, depart_id=? where id=?

      这里多了两句 update,要 注意:如果Employee.hbm.xml 中外键有非空约束,如下:保存时只能用" 第一种 "顺序,用了第二种,先插入员工,但depart_id字段为空,会异常,不能插入

    <many-to-one name="depart" column="depart_id" not-null="true"></many-to-one>

      我们来查询一个员工,注意"部门":

    //测试查询 
    public static void main(final String[] args){    
        final Employee em = query(7);  
        //员工的部门 , 执行Hibernate.initialize()后, 在session关闭前就取得了部门.  
        //若没有执行Hibernate.initialize(), 下面会抛异常.  
        System.out.println(em.getDepart().getName());  
    }  
    //查询一个员工出来 
    public static Employee query(final int id){  
        Session session = null;  
        try{  
            session = HibernateUtil.getSeesion();  
            final Transaction tx = session.beginTransaction();  
            final Employee em = (Employee) session.get(Employee.class, id); //按ID查  
            //因为 员工的 "部门" 属性会懒加载,  
            //在session关闭后,调用em.getDepart()无法取到部门信息  
            //所以这里用 Hibernate.initialize(em.getDepart()) 提前加载一下.  
            //是em.getDepart() 而不是em
            Hibernate.initialize(em.getDepart());  
            tx.commit();  
            return em;  
        }finally{   
            if (session != null){  
                session.close();  
            }  
        }  
    }

      输出的SQL是:

      Hibernate: select employee0_.id as id1_0_, employee0_.`name` as name2_1_0_, employee0_.depart_id as depart3_1_0_ from Employee employee0_ where employee0_.id=?

  • 相关阅读:
    could not detect mdm peripheral on hardware
    学习zynq的一些感受
    sdk添加新的C文件编译出错
    linux下驱动webcam
    转:fatal error: SDL/SDL.h: No such file or directory
    转:Unknown module(s) in QT: multimedia
    HFSS设计导入AD中
    REST(Representational state transfer)的四个级别以及HATEOAS介绍
    Servlet CDI Example Analysis
    Introduction and use of Cookie and Session(Cookie&Session的介绍和使用)
  • 原文地址:https://www.cnblogs.com/goloving/p/7612968.html
Copyright © 2011-2022 走看看