【SSH快速進階】——Hibernate 多對一映射 和 一對多映射

來源:互聯網
上載者:User

【SSH快速進階】——Hibernate 多對一映射 和 一對多映射


  上兩篇文章說了一對一映射,這裡說一下多對一 和 一對多的映射情況。

  

  現實中有很多情境需要用到多對一或者一對多,比如上面這兩個類圖所展現出來的,一般情況下,一個部門會有多名員工,一名員工只在一個部門任職。

多對一關聯映射

  在上面的情境中,對於Employee來說,它跟Department的關係就是多對一。

  PO對象

   Employee.java

public class Employee {    public int id;    public String name;    public Department department;    //getter、setter}

   Department.java

public class Department {    public int id;    public String name;    //getter、setter}


  配置多對一關聯性時,設計po類時,除了寫出最基本的屬性(比如Employee的id、name),在對應“多”的那個類(比如Employee.java)中添加對應“一”那個類的引用(比如上面的department)。


  對應檔

   Employee.hbm.xml

                                                                        

   Department.hbm.xml

                                                            


  對應檔中的內容基本上跟它關聯的類中的欄位都是對應的。主鍵配置在中,基本欄位配置在中,對其他類的引用配置在中。

  運行代碼執行的建表語句為:

alter table t_employee drop foreign key FKFDCF5A196E78D697drop table if exists t_departmentdrop table if exists t_employeecreate table t_department (id integer not null auto_increment, name varchar(255), primary key (id))create table t_employee (id integer not null auto_increment, name varchar(255), departmentid integer, primary key (id))alter table t_employee add index FKFDCF5A196E78D697 (departmentid), add constraint FKFDCF5A196E78D697 foreign key (departmentid) references t_department (id)


  從建表語句中可以看出來,t_employee表中的外鍵departmentid與t_department表中的主鍵相關聯。

  產生的表結構如下:

  


  下面進行簡單測試

  插入測試

session.beginTransaction();Department department=new Department();department.setName("資訊部");Employee employee1=new Employee();employee1.setName("小胡");employee1.setDepartment(department);Employee employee2=new Employee();employee2.setName("小玉");employee2.setDepartment(department);session.save(employee1);session.save(employee2);session.getTransaction().commit();


  一執行,發現報錯了:org.hibernate.TransientObjectException,一看錯誤就知道,這是因為department還在Transient狀態時,session是不能對其操作的。所以可以在事務提交之前先save一下department:

session.beginTransaction();Department department=new Department();department.setName("資訊部");Employee employee1=new Employee();employee1.setName("小胡");employee1.setDepartment(department);Employee employee2=new Employee();employee2.setName("小玉");employee2.setDepartment(department);session.save(department);           session.save(employee1);session.save(employee2);session.getTransaction().commit();


  這樣就可以成功插入了:

  


  還有一種更簡單的方法,就是在對應檔Employee.hbm.xml的中配置cascade屬性,值為"save-update"

   Employee.hbm.xml

                                                                        


  cascade表示兩個對象之間的操作為聯動關係,即對一個對象執行了操作之後,對其指定的級聯對象也要進行相同的操作。Hibernate文檔對cascade的解釋為:
  "cascade(級聯) (可選): 指明哪些操作會從父物件級聯到關聯的對象。它的值代表著Hibernate基本操作的名稱, persist, merge, delete, save-update, evict, replicate, lock, refresh……"


  查詢測試

session.beginTransaction();Employee employee=(Employee)session.load(Employee.class, 1);System.out.println("employee的name:"+employee.getName());System.out.println("department的name:"+employee.getDepartment().getName());session.getTransaction().commit();

  測試結果:

employee的name:小玉department的name:資訊部



一對多關聯映射

  既然Employee對Department的關係是多對一,那麼反之,Department對Employee就是一對多的關係。

  所以要在Department的PO類中增加一個Employee對象的集合。這個集合可以是set、list、map甚至array等容器,由於set中的對象不可重複,並且效能更高,所以一般用set。


  PO對象

   Department.java

public class Department {    public int id;    public String name;    public Set employees;    //getter、setter}

   Employee.java

public class Employee {    public int id;    public String name;    //getter、setter}


  對應檔

   Employee.hbm.xml

                                                            

   Department.hbm.xml

                                                                                                              


  對應檔Department.hbm.xml中添加了set標籤,對應Department類中的集合employees,表示一個Department對象對應多個Employee對象。


  插入測試

session.beginTransaction();Employee employee1=new Employee();employee1.setName("小玉玉");Employee employee2=new Employee();employee2.setName("小洋洋");Set employees=new HashSet();employees.add(employee1);employees.add(employee2);Department department=new Department();department.setName("資訊部");department.setEmployees(employees);session.save(employee1);session.save(employee2);session.save(department);session.getTransaction().commit();

  插入結果:

  


  查詢測試

session.beginTransaction();Department department=(Department)session.load(Department.class,1);System.out.println("department的name:"+department.getName());System.out.println("department的employee有:");for(Employee employee:department.getEmployees()){    System.out.print(" "+employee.getName());}session.getTransaction().commit();

  控制台輸出內容為:

Hibernate: select department0_.id as id0_0_, department0_.name as name0_0_ from t_department department0_ where department0_.id=?department的name:資訊部department的employee有:Hibernate: select employees0_.departmentid as departme3_1_, employees0_.id as id1_, employees0_.id as id1_0_, employees0_.name as name1_0_ from t_employee employees0_ where employees0_.departmentid=? 小洋洋 小玉玉


  由此可見,一對多的配置中,預設為消極式載入,相當於lazy=”true”。

  給對應檔中標籤的屬性lazy設定為false時,不會消極式載入,即查詢Department的時候,會把屬於該Department的Employee全部查詢出來。控制台輸出內容為:

Hibernate: select department0_.id as id0_0_, department0_.name as name0_0_ from t_department department0_ where department0_.id=?Hibernate: select employees0_.departmentid as departme3_1_, employees0_.id as id1_, employees0_.id as id1_0_, employees0_.name as name1_0_ from t_employee employees0_ where employees0_.departmentid=?department的name:資訊部department的employee有: 小洋洋 小玉玉


比較

  相同點:映射原理基本一致,建表時,都是在“多”的一端添加外鍵指向“一”的一端。

  區別:維護的關係不同
  多對一維護的關係:多指向一的關係,載入“多”的時候可以把“一”也載入出來;
  一對多維護的關係:一指向多的關係,載入“一”的時候可以把“多”也載入出來;


【 轉載請註明出處——胡玉洋《【SSH快速進階】——Hibernate 多對一映射 和 一對多映射》】
 

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.