`
wumingdlz
  • 浏览: 32876 次
  • 性别: Icon_minigender_1
  • 来自: 江苏
最近访客 更多访客>>
社区版块
存档分类
最新评论

Hibernate中one-to-one的深入学习

阅读更多
hibernate one to one laxy constrained 实现延时加载
在Hibernate中,one-to-one主要用于两个表共用相同的主键。
<hibernate-mapping>
<class
    name="User"
    table="user"
>
    <id
        name="userId"
        type="integer"
        column="user_id"
        length="11"
    >
        <generator class="increment" />
    </id>
......
    <!-- bi-directional one-to-one association to Card-->
    <one-to-one
        name="card"
        class="Card"
        constrained="true"
        outer-join="auto"
    />
</class>
<class
    name="Card"
    table="card"
    lazy="true"
>
    <id
        name="userId"
        column="user_id"
   >
        <generator class="foreign">
         <param name="property">user</param>
        </generator>
    </id>
......
    <!-- bi-directional one-to-one association to User-->
    <one-to-one
        name="user"
        class="User"
        constrained="true"
        outer-join="auto"
    />
</class>
</hibernate-mapping>
hbm.xml 生成工具默认生成mapping   没有上面红色部份( constrained="true"和 Lazy="true"):
在执行 from User 查询的同时会产生 from Card 查询。
或执行 from Card 查询的同时会产生 from User 查询。
如果添加了红色部份(实现延时加载):
在执行 from User 查询的同时不会产生 from Card 查询。
或执行 from Card 查询的同时不会产生 from User 查询。











1.关于one-to-one

    持久化对象之间一对一的关联关系是通过one-to-one元素定义:

<one-to-one
        name="propertyName"                                (1)
        class="ClassName"                                  (2)
        cascade="all|none|save-update|delete"              (3)
        constrained="true|false"                           (4)
        outer-join="true|false|auto"                       (5)
        property-ref="propertyNameFromAssociatedClass"     (6)
        access="field|property|ClassName"                  (7)
       
/>

(1)

name: 属性的名字[POJO中的]。
(2)

class (可选 - 默认是通过反射得到的属性类型):被关联的类的名字。
(3)

cascade(级联) (可选) 表明操作是否从父对象级联到被关联的对象。
(4)

constrained(约束) (可选) 表明该类对应的表对应的数据库表,和被关联的对象所对应的数据库表之间,通过一个外键引用对主键进行约束。这个选项影响save()和delete()在级联执行时的先后顺序(也在schema export tool中被使用)。
(5)

outer-join(外连接) (可选 - 默认为 自动): 当设置hibernate.use_outer_join的时候,对这个关联允许外连接抓取。
(6)

property-ref: (可选) 指定关联类的一个属性,这个属性将会和本外键相对应。如果没有指定,会使用对方关联类的主键[POJO中POJO类的实例]。
(7)

access (可选 - 默认是 property): Hibernate用来访问属性的策略。

2.one-to-one分类

主键关联

惟一外键关联

主键关联不需要额外的表字段;两行是通过这种一对一关系相关联的,那么这两行就共享同样的主关键字值。所以如果你希望两个对象通过主键一对一关联,你必须确认它们被赋予同样的标识值!

另一种方式是一个外键和一个惟一关键字对应。

3.one-to-one中惟一外键关联操作

(1)数据库DDL

#
# Table structure for table 'author'
#

CREATE TABLE author (
  author_id char(20) NOT NULL default '',
  person_id char(20) default NULL,
  PRIMARY KEY  (author_id)
) ENGINE=InnoDB DEFAULT CHARSET=gb2312;

#
# Table structure for table 'person'
#

CREATE TABLE person (
  person_id char(20) NOT NULL default '',
  name char(20) default NULL,
  PRIMARY KEY  (person_id)
) ENGINE=InnoDB DEFAULT CHARSET=gb2312;

(2)映射文件

Author.hbm.xml

<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
                            "-//Hibernate/Hibernate Mapping DTD 2.0//EN"
                            "http://hibernate.sourceforge.net/hibernate-mapping-2.0.dtd" >

<!-- DO NOT EDIT: This is a generated file that is synchronized -->
<!-- by MyEclipse Hibernate tool integration.                   -->
<!-- Created Sat Apr 23 14:28:37 CST 2005                         -->
<hibernate-mapping package="po">

    <class name="Author" table="author">
        <id name="authorId" column="author_id" type="java.lang.String">
            <generator class="assigned"/>
        </id>
      
        <many-to-one
   cascade="all"
   class="po.Person"
   column="person_id"
   name="person"
   not-null="true"
   outer-join="auto"
   unique="true"
   />
      
    </class>
  
</hibernate-mapping>

Person.hbm.xml

<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
                            "-//Hibernate/Hibernate Mapping DTD 2.0//EN"
                            "http://hibernate.sourceforge.net/hibernate-mapping-2.0.dtd" >

<!-- DO NOT EDIT: This is a generated file that is synchronized -->
<!-- by MyEclipse Hibernate tool integration.                   -->
<!-- Created Sat Apr 23 14:28:39 CST 2005                         -->
<hibernate-mapping package="po">

    <class name="Person" table="person">
        <id name="personId" column="person_id" type="java.lang.String">
            <generator class="assigned"/>
        </id>

        <property name="name" column="name" type="java.lang.String" />
      
        <one-to-one name="author" class="Author" property-ref="person"/>
      
    </class>
  
</hibernate-mapping>

(2)POJO文件

AbstractAuthor.java

package po;

import java.io.Serializable;

public abstract class AbstractAuthor
    implements Serializable
{
    /** The cached hash code value for this instance.  Settting to 0 triggers re-calculation. */
    private int hashValue = 0;

    /** The composite primary key value. */
    private java.lang.String authorId;

    /** The value of the simple personId property. */
    private java.lang.String personId;

    /**
     * Simple constructor of AbstractAuthor instances.
     */
    public AbstractAuthor()
    {
    }

    /**
     * Constructor of AbstractAuthor instances given a simple primary key.
     * @param authorId
     */
    public AbstractAuthor(java.lang.String authorId)
    {
        this.setAuthorId(authorId);
    }

    /**
     * Return the simple primary key value that identifies this object.
     * @return java.lang.String
     */
    public java.lang.String getAuthorId()
    {
        return authorId;
    }

    /**
     * Set the simple primary key value that identifies this object.
     * @param authorId
     */
    public void setAuthorId(java.lang.String authorId)
    {
        this.hashValue = 0;
        this.authorId = authorId;
    }

    /**
     * Return the value of the person_id column.
     * @return java.lang.String
     */
    public java.lang.String getPersonId()
    {
        return this.personId;
    }

    /**
     * Set the value of the person_id column.
     * @param personId
     */
    public void setPersonId(java.lang.String personId)
    {
        this.personId = personId;
    }

    /**
     * Implementation of the equals comparison on the basis of equality of the primary key values.
     * @param rhs
     * @return boolean
     */
    public boolean equals(Object rhs)
    {
        if (rhs == null)
            return false;
        if (! (rhs instanceof Author))
            return false;
        Author that = (Author) rhs;
        if (this.getAuthorId() != null && that.getAuthorId() != null)
        {
            if (! this.getAuthorId().equals(that.getAuthorId()))
            {
                return false;
            }
        }
        return true;
    }

    /**
     * Implementation of the hashCode method conforming to the Bloch pattern with
     * the exception of array properties (these are very unlikely primary key types).
     * @return int
     */
    public int hashCode()
    {
        if (this.hashValue == 0)
        {
            int result = 17;
            int authorIdValue = this.getAuthorId() == null ? 0 : this.getAuthorId().hashCode();
            result = result * 37 + authorIdValue;
            this.hashValue = result;
        }
        return this.hashValue;
    }
}

Author.java

package po;

import java.io.Serializable;

public class Author
    extends AbstractAuthor
    implements Serializable
{
    private Person person;

/**
     * Simple constructor of Author instances.
     */
    public Author()
    {
    }

    /**
     * Constructor of Author instances given a simple primary key.
     * @param authorId
     */
    public Author(java.lang.String authorId)
    {
        super(authorId);
    }

    /* Add customized code below */
public void setPerson(Person person){
  this.person=person;
}
public Person getPerson(){
  return person;
}

}

AbstractPerson.java

package po;

import java.io.Serializable;

public abstract class AbstractPerson
    implements Serializable
{
    /** The cached hash code value for this instance.  Settting to 0 triggers re-calculation. */
    private int hashValue = 0;

    /** The composite primary key value. */
    private java.lang.String personId;

    /** The value of the simple name property. */
    private java.lang.String name;

    /**
     * Simple constructor of AbstractPerson instances.
     */
    public AbstractPerson()
    {
    }

    /**
     * Constructor of AbstractPerson instances given a simple primary key.
     * @param personId
     */
    public AbstractPerson(java.lang.String personId)
    {
        this.setPersonId(personId);
    }

    /**
     * Return the simple primary key value that identifies this object.
     * @return java.lang.String
     */
    public java.lang.String getPersonId()
    {
        return personId;
    }

    /**
     * Set the simple primary key value that identifies this object.
     * @param personId
     */
    public void setPersonId(java.lang.String personId)
    {
        this.hashValue = 0;
        this.personId = personId;
    }

    /**
     * Return the value of the name column.
     * @return java.lang.String
     */
    public java.lang.String getName()
    {
        return this.name;
    }

    /**
     * Set the value of the name column.
     * @param name
     */
    public void setName(java.lang.String name)
    {
        this.name = name;
    }

    /**
     * Implementation of the equals comparison on the basis of equality of the primary key values.
     * @param rhs
     * @return boolean
     */
    public boolean equals(Object rhs)
    {
        if (rhs == null)
            return false;
        if (! (rhs instanceof Person))
            return false;
        Person that = (Person) rhs;
        if (this.getPersonId() != null && that.getPersonId() != null)
        {
            if (! this.getPersonId().equals(that.getPersonId()))
            {
                return false;
            }
        }
        return true;
    }

    /**
     * Implementation of the hashCode method conforming to the Bloch pattern with
     * the exception of array properties (these are very unlikely primary key types).
     * @return int
     */
    public int hashCode()
    {
        if (this.hashValue == 0)
        {
            int result = 17;
            int personIdValue = this.getPersonId() == null ? 0 : this.getPersonId().hashCode();
            result = result * 37 + personIdValue;
            this.hashValue = result;
        }
        return this.hashValue;
    }
}

Person.java
package po;

import java.io.Serializable;

public class Person
    extends AbstractPerson
    implements Serializable
{
    private Author author;
/**
     * Simple constructor of Person instances.
     */
    public Person()
    {
    }

    /**
     * Constructor of Person instances given a simple primary key.
     * @param personId
     */
    public Person(java.lang.String personId)
    {
        super(personId);
    }

    /* Add customized code below */
public void setAuthor(Author author){
  this.author=author;
}
public Author getAuthor(){
  return author;
}

}

(3)测试文件

TestOO.java

package test;

import po.Author;
import po.Person;

import net.sf.hibernate.*;
import net.sf.hibernate.cfg.*;


public class TestOO {

private Session sesssion=null;

/**
  * @param args
  */
public static void main(String[] args) {
  // TODO Auto-generated method stub
  try {
       Configuration cfg = new Configuration().configure();
       SessionFactory sessions = cfg.buildSessionFactory();
       Session session = sessions.openSession();
       Transaction tx = session.beginTransaction();
     
       Person person = new Person();
        
       person.setPersonId("1");
    person.setName("Blake Stone");
        
       Author author = new Author();

       author.setAuthorId("11");
    author.setPerson(person);

      
   session.save(person);
   session.save(author);
   System.out.print("i will dead if i don't get success!");
    
       tx.commit();
      session.close();
     } catch (Exception e) {
      System.out.println(e);
     }
   }
}

(4)分享喜悦

     运行测试类,数据正常添加进数据库。

(5)深入探讨

     a.由于主键采用assigned方式,必须自己指定ID;

    b.如果只采用session.save(author);将会产生级联错误[ Could not synchronize database state with session             net.sf.hibernate.HibernateException: Batch update row count wrong: 0],看看执行的SQL语句[Hibernate: insert into author (person_id, author_id) values (?, ?)   Hibernate: update person set name=? where person_id=?]很明白是吧,因为person表还是空的,当然执行update操作会失败!虽然解决的方法很简单,可问题值得思考!虽然对person进行了setter方法,可不要忘了他仍旧是VO而不是PO!
分享到:
评论

相关推荐

    Hibernate Mapping Many-to-One 实例 内附源代码及附件下载

    本实例将详细讲解如何在Hibernate中实现Many-to-One关系映射,这是一种常见的数据库关联,表示一个实体可以与多个其他实体相关联。 在Many-to-One关系中,通常一个实体(如部门)可以有多个相关实体(如员工),而...

    hibernate 全面学习->hibernate 关联映射学习

    本篇文章将全面探讨Hibernate的关联映射学习,包括一对一(One-to-One)、一对多(One-to-Many)、多对一(Many-to-One)以及多对多(Many-to-Many)四种关系映射。 首先,一对一关联映射(One-to-One)是两个实体...

    hibernate中基于外键的one2one

    在Java的持久化框架Hibernate中,一对一(One-to-One)关系映射是一种常见的实体关联方式。基于外键的One-to-One映射是其中的一种实现方式,它通过在一方或双方实体的表中添加外键来建立关联。接下来,我们将深入...

    hibernate-distribution-3.6.10.Final-dist

    8. **一对多(One-to-Many)、多对一(Many-to-One)和多对多(Many-to-Many)关系**:Hibernate通过`@OneToMany`,`@ManyToOne`,`@ManyToMany`注解来处理这些关联关系,自动建立关联表或中间表。 9. **事务管理**...

    Hibernate one to one 实例

    在Java的持久化框架Hibernate中,一对一(One-to-One)关联是一种常见的关系映射方式,它表示两个实体之间存在唯一的对应关系。这种关系通常出现在两个实体之间具有唯一性的关联,例如一个人与他的护照,或者一个...

    Hibernate学习要点_one2one 一对一主键双线关联

    在深入探讨Hibernate中的一对一(One-to-One)主键双线关联机制之前,我们首先需要理解几个核心概念:Hibernate框架、实体关系映射以及主键关联的基本原理。Hibernate是Java平台下的一款开源对象关系映射(ORM)框架...

    Hibernate-One-To-One-JavaFx:此存储库包含使用 Java、Hibernate 和 JavaFX 创建一对一映射 GUI 应用程序的示例代码

    在本项目中,“Hibernate-One-To-One-JavaFx”是一个演示如何使用Java、Hibernate ORM框架以及JavaFX库构建一个一对一关系的图形用户界面(GUI)应用程序的实例。让我们深入探讨其中涉及的关键技术点。 1. **...

    学习hibernate必看ppt--总结的很全面

    2. **关联映射**:Hibernate支持多种关系映射,包括一对一(One-to-One)、一对多(One-to-Many)、多对一(Many-to-One)和多对多(Many-to-Many)。这部分可能详细解释了这些关系的配置,以及在Java对象和数据库表...

    hibernate 关联映射(一) many to one

    本文将深入探讨“Hibernate关联映射中的Many-to-One关系”。 Many-to-One关联是现实世界中常见的关系类型,比如一个学生可以对应多个课程,而一个课程可能被多个学生选修。在数据库中,这通常表现为一对多(One-to-...

    hibernate one to one一对一关系示例

    在Java的持久化框架Hibernate中,一对一(One-to-One)关联是对象关系映射(ORM)中的一个重要概念。这种关联关系意味着一个实体最多只能与另一个实体的实例进行关联,反之亦然。本示例将深入讲解如何在Hibernate中...

    Hibernate之第3解之-hibernate_hibernate_many2one_1

    本篇将重点探讨Hibernate中的Many-to-One关系映射,帮助开发者更深入地理解和运用这一关键特性。 Many-to-One关系是现实世界中常见的关联类型,一个实体可能对应另一个实体的多个实例,例如,一个员工可以属于一个...

    Hibernate-api Hibernate文档

    Hibernate 是一个开源的对象关系映射...通过深入学习这份Hibernate-api文档,开发者能够熟练掌握Hibernate的核心概念、配置、查询机制以及对象关系映射,从而在实际项目中更加自如地运用Hibernate这一强大的ORM工具。

    Expert_One-on-One_J2EE_Development_without_EJB中文版 part10

    《Expert One-on-One J2EE Development without EJB中文版 part10》这本书是Java开发领域的一本重要参考资料,尤其对于那些希望深入理解J2EE(Java 2 Platform, Enterprise Edition)开发但不依赖EJB(Enterprise ...

    Hibernate中文Api最新参考文档

    关联映射是Hibernate的一大特色,它允许我们将一个实体与另一个或多个实体建立关系,如一对一(One-to-One)、一对多(One-to-Many)、多对一(Many-to-One)、多对多(Many-to-Many)。这些关联可以通过属性或集合...

    Hibernate 3.6.0.Final Reference PDF 手册

    - **Mapping one-to-one and one-to-many associations**:一对一和一对多关联的映射。 - **自然ID(natural-id)**:使用自然标识符代替主键。 - **Any**:任意类型的映射。 - **属性**:其他属性设置,如懒...

    hibernate学习笔记文档

    - 在 XML 映射文件中使用 `&lt;one-to-many&gt;` 或 `&lt;many-to-many&gt;` 标签来配置这些关系。 - **查询操作**: - 使用 HQL(Hibernate Query Language)或 Criteria API 来执行复杂查询。 - 支持分页查询、动态查询等...

    基于注解的关联关系Hibernate

    在这个“基于注解的关联关系Hibernate”的主题中,我们将深入探讨如何使用Hibernate的注解来配置不同类型的关联关系,包括一对一(One-to-One)、一对多(One-to-Many)、多对一(Many-to-One)和多对多(Many-to-...

    hibernate学习总结

    - **一对一(One-to-One)**: 一个实体对应另一个实体的一条记录。 - **一对多(One-to-Many)**: 一个实体对应多个实体的记录。 - **多对一(Many-to-One)**: 多个实体对应另一个实体的一条记录。 - **多对多...

Global site tag (gtag.js) - Google Analytics