续set映射自定义对象的用法
element标签:使用在能直接映射到表中的hibernate支持的java类型数据
one-to-many、many-to-one:使用在映射自定义类中
- One to Many映射关系
- 单向多对一外键关联(XML/Annotation)(xml和annotation都实现了)
- 单向一对多外键关联(XML/Annotation) (xml和annotation都实现了)
- 双向一对多外键关联(XML/Annotation) (xml和annotation都实现了)
注: Project中使用XML/Annotation时应统一
一、单向多对一
例子:一个人有多本书,每本书对应一个人,能通过书查找修改人的信息,不能通过人查找修改书的信息,Book为多的一方,只需要在Book原有的xml中添加many-to-one映射自定义类
类属性变化:Book类中要添加User类的对象,并提供get和set方法,User类无需修改属性
- XML:
Book类
<hibernate-mapping>
<class name="entity.Book" table="hbn_bookr" >
<many-to-one name="user" class="entity.User" column="user_id"/>
</class><!--name属性名,class属性对应的类位置,类名大写,column字段名-->
</hibernate-mapping>
- Annotation:
Book类
@ManyToOne()
@JoinColumn(name="user_id",referencedColumnName="id")
//name外键列的字段名,referencedColumnName是关联少的一方的属性名
private User user;
注:单向多对一注解如果不添加@JoinColumn(),新增字段名则会按默认的关联属性名_id
二、单向一对多
例子:一个人有多本书,每本书对应一个人,能通过人查找修改书,不能通过书查找修改人的信息,
类属性变化:User中要添加泛型为Book类的set集合,用来存储多个书的对象,提供get和set方法,Book类无需修改属性
- XML:
User类
<hibernate-mapping>
<class name="entity.User" table="hbn_user" >
<set name="books"> <!--name属性名,class属性对应的类位置-->
<key column="uid"/> <!--比较特殊,会在多的一方添加外键列维护,取字段名为少的一方-->
<one-to-many class="entity.Book"/>
</set>
</class>
</hibernate-mapping>
- Annotation:
User类
@OneToMany()
@JoinColumn(name="uid")
private Set<Book> books = new HashSet<Book>();
//set不可存储重复的值,提前初始化,方便用get存值
注:单向一对多注解如果不添加@JoinColumn(),则会自动生成以"少的一方的表名_多的一方的表名"命名的表来维护关系,如hbn_user_hbn_book,如果添加注解,像上述代码,则仍然会在多的一方添加column维护关系
三、双向一对多:
例子:每本书对应一个人,一个人对应多本书,可相互查找并修改信息,主要多的一方维护,少的一方响应
类属性变化:Book类添加User属性,User类添加泛型为Book的set属性,提供get和set方法
- XML: 注意两个类的xml中的column都需要以少的一方命名(key标签和many-to-one标签加入的字段保持一致),否者会在多的一方表中产生两个字段列,造成冗余,因为单向一对多也是通过在多的一方添加外键列来维护关系的,可设置在一的一方inverse="true"让出管理关系权,让多的一方管理
Book类
<hibernate-mapping>
<class name="entity.Book" table="hbn_bookr" >
<many-to-one name="user" class="entity.User" column="uid"/>
</class><!--name属性名,class属性对应的类位置,类名大写,column字段名-->
</hibernate-mapping>
User类
<hibernate-mapping>
<class name="entity.User" table="hbn_user" >
<set name="books" inverse="true"> <!--name属性名-->
<key column="uid"/> <!--比较特殊,会在多的一方添加外键列维护,取字段名为少的一方-->
<one-to-many class="entity.Book" /><!--class属性对应的类位置-->
</set>
</class>
</hibernate-mapping>
- Annotation:
Book类
@ManyToOne()
@JoinColumn(name="uid",referencedColumnName="id")//在Book类的表中生成uid,是关联Userid的外键
private User user;
User类
@OneToMany(mappedBy="user") //相当于inverse=true,让出关系维护权给book类
private Set<Book> books = new HashSet<Book>();
注:单向关系的缺点还是比较明显的,比如一对多单向,多的那一方没有任何关于另一方的信息,多对一单向则是反之。所以正常使用时,双向一对多是最常用的,双方都有彼此的信息。
资料来源:
单向多对一映射
单向一对多映射和双向一对多映射