如圖,當多個對象之間有類似的屬性的時候,可以將其公用的屬性進行抽離:
拿User和Employee對象舉例,此時User和Employee中的公用屬性已經被抽離到一個單獨的對象“Comtact”當中,但是此時數據表仍然如下:
由此可見,Component這種映射的方法,在對象模型中“細粒度”,在關系模型中仍然是“粗粒度”。
代碼實現:
(1)實體
1.抽取的公共類Contact
public class Contact { PRivate String email; private String address; private String zipCode; private String contactTel; public String getEmail() { return email; } public void setEmail(String email) { this.email = email; } public String getAddress() { return address; } public void setAddress(String address) { this.address = address; } public String getZipCode() { return zipCode; } public void setZipCode(String zipCode) { this.zipCode = zipCode; } public String getContactTel() { return contactTel; } public void setContactTel(String contactTel) { this.contactTel = contactTel; }} 2.User類public class User { private String id; private String name; private Contact userContact; public Contact getUserContact() { return userContact; } public void setUserContact(Contact userContact) { this.userContact = userContact; } public String getId() { return id; } public void setId(String id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; }} 3.Employee類public class Employee { private int id; private String name; private Contact employeeContact; public Contact getEmployeeContact() { return employeeContact; } public void setEmployeeContact(Contact employeeContact) { this.employeeContact = employeeContact; } public int getId() { return id; } public void setId(int id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; }} 由此可見,Contact單獨抽取之后,在User和Employee中,將Contact作為引用,成為其中的一個屬性,并生成對應get和set方法。(2).hbm.xml配置文件
<hibernate-mapping> <class name="com.bjpowernode.hibernate.Employee" table="t_emplyee"> <id name="id"> <generator class="native"/> </id> <property name="name"/> <component name="employeeContact"> <property name="email"/> <property name="address"/> <property name="zipCode"/> <property name="contactTel"/> </component> </class> <class name="com.bjpowernode.hibernate.User" table="t_user"> <id name="id"> <generator class="native"/> </id> <property name="name"/> <component name="employeeContact"> <property name="email"/> <property name="address"/> <property name="zipCode"/> <property name="contactTel"/> </component> </class></hibernate-mapping>由此可見,在該hbm.xml當中,主鍵生成策略為"native",正常的name屬性之后,加入<component>關聯屬性,子標簽中加入<email><address>等子屬性。
(3)存儲、加載測試
public void testSave1(){ session session = null; try{ session = HibernateUtils.getSession(); session.beginTransaction(); User user = new User(); user.setName("張三"); Contact userContact = new Contact(); userContact.setAddress("address"); userContact.setContactTel("contactTel"); userContact.setEmail("email"); userContact.setZipCode("zipCode"); user.setUserContact(userContact); session.save(user); session.getTransaction().commit(); }catch(Exception e){ e.printStackTrace(); }finally{ HibernateUtils.closeSession(session); }} 分別實例化User和Contact對象并復制,將Contact對象關聯到User當中后,直接session.save(user)即可,因為表中實際只有一張表,不會因對象狀態出現Exception問題。同理,加載方法如下:
public void testLoad1(){ Session session = null; try{ session = HibernateUtils.getSession(); session.beginTransaction(); User user = (User)session.load(User.class, 1); System.out.println(user.getName()); System.out.println(user.getUserContact().getAddress()); session.save(user); session.getTransaction().commit(); }catch(Exception e){ e.printStackTrace(); }finally{ HibernateUtils.closeSession(session); }} 通過加載User對象,即可加載出Contact中的內容。總結:
采用Component的好處在于,實現對象模型的細粒度劃分,復用率更高,層次更加分明。
新聞熱點
疑難解答