轉:hibernate關聯關係映射

來源:互聯網
上載者:User

1、單向N-1

2、單向1-1

3、單向1-N

4、單向N-N

5、雙向1-N

6、雙向N-N

7、雙向1-1

下面就對這七種關聯關係映射進行一個簡單的總結:

一、單向的多對一

看兩個POJO

public class Person{

private int pid;

private String name;

private Address address;

...//產生相應的getter、setter方法

}

----------------------------------------

public class Address{

private int id;

private String detail;

...//產生相應的getter、setter方法

}

這裡我們需要維護的關係是多個Person可以對應同一個地址,使用單向的N-1映射我們只需要在多的一端加入一個外鍵指向一的一端即可

**看設定檔

<class name="Person">

<id name="id">

<generator class="native"/>

</id>

...//部分欄位配置省略

<many-to-one name="address" column="addressId"/>//關鍵配置

</class>

這樣配置以後hibernate就會幫我們在多的一端(Person)添加一個外鍵addressId指向一的一端

二、單向的1-1(外部索引鍵關聯)

可以採用<many-to-one>標籤,指定多的一端的unique=true,這樣就限制了多的一端的多重性唯一

通過這種手段映射一對一唯一外部索引鍵關聯

設定檔只需要修改為:

<many-to-one name="address" column="addressId" unique="true"/>

三、單向的1-N

**看代碼,我們知道一個班級有多名學生,這就是一個典型的1-N關係

public class Classes {
private int id;
private String name;
private Set students;

...//產生相應的getter、setter方法

}

---------------------------------------------------------------------------

public class Student {
private int id;
private String name;

..//產生相應是getter、setter方法

}

**映射原理:一對多關聯映射,在多的一端添加一個外鍵指向一的一端,它維護的關係是一指向多

**設定檔:

<class name="Classes" table="t_classes">
   <id name="id">
    <generator class="native"/>
   </id>
   <property name="name"/>
   <set name="students">
    <key column="classesid"/>//在一的一端添加的外鍵指向多的一端(預設情況下市主鍵匹配)
    <one-to-many class="xxx.Student"/>//注意它維護的是一指向多的關係
   </set>
</class>

四、雙向1-N

上面提到了單向的1-N在一的一端添加的外鍵指向多的一端即可,對於雙向的1-N則類似於N-N,集合元素中不使用<one-to-many>

元素映射關聯屬性,而使用<many-to-many>元素,但是為了保證一的一端,因此需要增加unique="true"屬性

**配置,簡單修改單向1-N的設定檔

<class name="xxx.Classes" table="t_classes">
   <id name="id">
    <generator class="native"/>
   </id>
   <property name="name"/>
   <set name="students">
    <key column="classesid"/>

    <many-to-many class="xxx.Student" unique="true"/>
   </set>
</class>

五、單向多對多

**先看兩個POJO

public class User {
private int id;
private String name;
private Set roles;

..//產生相應的getter、setter方法

}

---------------------------------------------------------------------------

public class Role {
private int id;
private String name;

..//產生相應的getter、setter方法

}

現在需要映射這樣的N-N關係,一個User可以有多個Role,而一個Role有可以被多個User所擁有

這樣我們就可以將一個N-N關係拆分為兩個N-1的關係

**看設定檔

<class name="xxx.User" table="t_user">
   <id name="id">
    <generator class="native"/>
   </id>
   <property name="name"/>
   <set name="roles" table="t_user_role">
    <key column="userid"/>
    <many-to-many class="xxx.Role" column="roleid"/>
   </set>
</class>

這樣我們的關係的明確了

   t_user               t_user_role                     t_role     

id name    < -------userid     roleid    ----- >      id     name

六、雙向的多對多關係

雙向的多對多映射需要在兩邊都增加集合元素,用於映射集合屬性

修改上面的單向N-N映射

在Role中添加集合屬性

public class Role {
private int id;
private String name;

privarte Set user

..//產生相應的getter、setter方法

}

修改設定檔

<class name="xxx.User" table="t_user">
   <id name="id">
    <generator class="native"/>
   </id>
   <property name="name"/>
   <set name="roles" table="t_user_role">
    <key column="userid"/>
    <many-to-many class="xxx.Role" column="roleid"/>
   </set>
</class>

------------------------------------------------------------------------------------------------

<class name="xxx.Role" table="t_role">
   <id name="id">
    <generator class="native"/>
   </id>
   <property name="name"/>
   <set name="users" table="t_user_role" order-by="userid">
    <key column="roleid"/>
    <many-to-many class="xxx.User" column="userid"/>
   </set>
</class>

注意點:1、雙向多對多關聯兩邊都需要指定串連表的表名和外鍵列的列名

           2、兩個集合元素Set的table值必須指定,而且需要相同

七、雙向的一對一關聯

雙向的1-1關聯有兩種形式:

1、基於外鍵的雙向1-1關聯

我們可以回想一下上面提到的單向1-1映射,它是有N-1的一個特例,只需要在<many-to-one>標籤多的一端添加unique="true"屬性就可以形成單向的1-1映射關係,那麼該怎麼樣將這種映射改為雙向的呢?

下面我們再舉個例子:一個User必須要有一個唯一的identityId

首先建立兩個POJO類

public class Person {

private int id;
private String name;
private IdentityId identityId;

..//產生相應的getter、setter方法

}

public class IdentityId {
private int id;
private String cardNo;
private Person person;

..//產生相應的getter、setter方法

}

**看設定檔

<class name="xxx.Person" table="t_person">
   <id name="id">
    <generator class="native"/>
   </id>
   <property name="name"/>
   <many-to-one name="identityId" class="xxx.IdentityId" unique="true"/>
</class>

-----------------------------------------------------------------------------------

<class name="xxx.IdentityId" table="t_identity">
   <id name="id">
    <generator class="native"/>
   </id>
   <property name="cardNo"/>
   <one-to-one name="person" class="xxx.Person" property-ref="identityId"/>
</class>

注意:這裡的property-ref屬性為identity表明建立了從identity對象到person對象的關聯.

因此只要調用identity持久化對象的getIdentityId()方法就可以導航到Person對象 由此可見:

Person對象和IdentityId對象之間為雙向的關聯關係person.getIdentityId().getPerson()

2、基於主鍵的1-1雙向關聯

上面的POJO類不需要有任何變化,我們只需要修改設定檔

<class name="xxx.Person" table="t_person">
   <id name="id" column="ID">
    <generator class="foreign">
     <param name="property">identityId</param>
    </generator>
   </id>
   <property name="name"/>
   <one-to-one name="identity" clsss="xxx.IdentityId" constrained="true"/>
</class>

注意:這裡的constrained="true"表明Person表的主鍵ID同時作為外鍵參考IdentityId表

--------------------------------------------------------------------------------------

<class name="xxx.Identity" table="t_identity">
   <id name="id">
    <generator class="native"/>
   </id>
   <property name="cardNo"/>
   <one-to-one name="person" class="xxx.Person"/>
</class>

注意:這裡Person表中ID既是主鍵同時還作為外鍵參照表IdentityId,因為使用了foreign標識符建置原則Hibernate就保證了Person

對象與關聯的IdentityId對象共用一個主鍵

綜上所述,hibernate的實體映射方式很靈活,如果我們使用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.