一、对象之间的关系
1 这里的关系映射指的是对象之间的关系,并不是指数据库的关系,本章解决的问题是当对象之间处于
下列关系之一时,数据库表该如何映射,编程上该如何对待(红色为重点中的重点)
a) 怎么写 Annotation
b) 增删改査CRUD怎么写
a) 单向(主键、外键)
b) 双向(主键、外键)
c) 中间表
a) 一张主表,多张子表
a) @Embeddable
二、一对一关联
a) 项目名称:hibernate_0600_one2one_uni_fk
b) Annotation: 在被约束表字段的get方法上加@0ne20ne @JoinColumn
@OneToOne
@JoinColumn(name="wifeid")//指定生成的数据库字段名
public WifegetWife() {
return wife;
}
c) xml: 在被约束表的xml配置文件中加<many-to-one unique=true
<classname="com.bjsxt.pojo.StuIdCard">
<id name="id">
<generatorclass="native"></generator>
</id>
<property name="num"/>
<many-to-one name="student"column="studentId" unique="true">
</many-to-one>
</class>
unique="true"是保证生成的字段唯一,这样<many-to-one 也达到了一对一的效果
a) 项目名称:hibernate_0700_one2one_bi_fk^
b) Annotation: @0ne20ne(mappedBy=”另一个类里定义的属性名”)
规律:凡是双向关联,必设mappedBy
在Wife类中 写Husband对象属性并添加注解@OneToOne(mappedBy="wife") mappedBy作用是指定这个一对一关联是被Husband类的 wife属性(准确说是getWife方法)做的映射
@OneToOne(mappedBy="wife")
public Husband getHusband() {
return husband;
}
在类中写Wife对象属性
@OneToOne
@JoinColumn(name="wifeid")//指定生成的数据库字段名
public WifegetWife() {
return wife;
}
此注释将由Husband表中生成wifeid字段作为fk外键,wife表中不生成额外的Husbandid字段
c) xml: many-to-one unique <one-to-one property-ref
在Student类中写StuIdCard属性, StuIdCard类中写Student属性
StuIdCard.hbm.xml文件中加
<many-to-onename="student" column="studentId"unique="true"></many-to-one>
Student.hbm.xml文件中加
<one-to-onename="stuIdCard"property-ref="student"></one-to-one>
其中, property-ref 相当于mappedBy
此方式生成的StuIdCard表中包含studentid字段作为fk外键, Student表中不生成额外的字段
特别说明: 一对一单向外键关联与一对一双向外键关联在数据库的表的格式是一样的,区别在于java程序中. 双向外键关联可通过Hibernate在两个类间互相调用彼此,而单向外键关联只能单方向调用.
3 一对一单向主键关联(不重要,忘记)
a) 项目名称:hibernate_0800_one2one_uni_pk
b) @primaryKeyJoinColumn
c) xml: <one-to-one id 使用 foreign class
4 一对一双向主键关联(不重要,忘记)
a) 项目名称:hibernate_0900_one2one_bi_pk
b) @primaryKeyJoinColumn(不常用,了解)
c) xml: <one-to-one id 使用foreign class和<one-to-oneproperty-ref
a) 项目名称:hibernate_1000_one2one_uni_fk_composite
b) @JoinColumns
Wife类中建立联合主键,建立方式参考 ID生成策略中的联合主键部分
Husband类中写Wife对象属性,并在其get方法上写@OneToOne即可完成一对一外键映射
若想要指定生成的外键名则需使用@JoinColumns注解,如下:
@OneToOne
@JoinColumns( { @JoinColumn(name ="wifeid", referencedColumnName = "id"),
@JoinColumn(name ="wifename", referencedColumnName = "name") })
/*@JoinColumns用于在一对一外键关联存在联合主键情况时指定生成的外键字段名称
@JoinColumns的参数为@JoinColumn数组 @JoinColumn内除需指定name属性外还需指定
referencedColumnName属性值作用是可指定生成的字段名所对应的目标表字段名*/
public Wife getWife() {……}
三、组件映射
1 项目:hibernate_1100_component
2 对象关系:一个对象是另外一个对象的一部分
4 annotation: @ Embeddable @Embbeded
对象模型
Husband(id,name,wife)
Wife(name,age)
Annotation:
在Husband的wife属性上建立注解
@Embedded表明该对象是从别的位置嵌入过来的,是不需要单独映射的表.
这种方式生成的表为husband(id,name,wifename,wifeage),不会生成wife表.
@Embedded
Public Wift getWife(){
}
@AttributeOverride注解需要写在getWife方法上,可以重新指定生成的Wife类组件生成的字段名,例如:Husband与Wife两个类中都有name字段,这样在生成表的时候会有冲突,此时采用@AttributeOverride注解可以指定Wife类中的name属性对应新的字段名—“wifename”,不过@AttributeOverride注解不常用,因为有更好的解决方法.1:不要在组件的两个映射类中写同名属性;2:如果真的有重复,那么可以在分类中(此处为Wife类)的重复名称的属性上使用如下内容以指定新的字段名:
@Column(name="wifename")
public String getName() {
return name;
}
另外,@Embeddable注解好像是写在分类(Wife类)的类名前的,不过好像不写也行
@Embeddable
public classWife {… …}
5 xml: 使用<component,例如:
<classname="Husband" >
<idname="id">
<generatorclass="native"/>
</id>
<propertyname="name"></property>
<componentname="wife">
<propertyname="wifeName"/>
<propertyname="wifeAge"/>
</component>
</class>