Hibernate映射基础
Hibernate-mapping/class/id/generator/property
Hibernate ID生成器
Hibernate内置ID生成器、自定义ID生成器
Hibernate数据类型
基本数据类型、JDBC数据类型、自定义数据类型
Hibernate对象生命周期
三种状态特征、区分、转换,持久态对象特性
理解各个关联关系映射中数据建模
掌握并熟练应用一对一关联
掌握并熟练应用一对多关联
掌握并熟练应用多对多关联
ORM映射规则
一对一关联
一对多关联
多对多关联
1. 映射概述
a) 类/表映射
b) 属性/字段映射
c) Map class associations to tables’ foreign key relationships
1:1/1:m/m:n
d) Map objects (instances of classes) to table rows
1. 一对一关联包括两种实现形式:
a) 唯一外键关联
b) 共享主键关联
2. 唯一外键关联
a) 唯一外键关联的一对一关系只是一对多关系的一个特例;
b) 唯一外键的实现是通过一方的主键作为另一方关联表的外键,并对外键做唯一性限制;
3. 唯一外键关联样例—数据模型
4. 唯一外键关联样例—POJO类片段
package com.oracle.entity;
public class Order {
private Integer Id;
private String name;
private Integer cost;
private Date createdDate;
private Address addr;
public Address getAddr() {
return addr;
}
public void setAddr(Address addr) {
this.addr = addr;
}
}
package com.oracle.entity;
public class Address {
private Integer Id;
private String street;
private String city;
private String zip;
private Order order;
public Order getOrder() {
return order;
}
public void setOrder(Order order) {
this.order = order;
}
}
5. 唯一外键关联样例—映射配置文件
6. 唯一外键关联样例-摘要
7. 共享主键关联
a) 如果两张表是通过这种一对一关系相关联的,那么这两张表就共享同样的主关键字值
b) Hibernate中,通过one-to-one节点对一对一关系进行定义
8. 主键关联样例—数据模型
9. 共享主键关联样例—POJO类片段
package com.oracle.entity;
public class Order {
private Integer Id;
private String name;
private Integer cost;
private Date createdDate;
private Address addr;
public Address getAddr() {
return addr;
}
public void setAddr(Address addr) {
this.addr = addr;
}
}
package com.oracle.entity;
public class Address {
private Integer Id;
private String street;
private String city;
private String zip;
private Order order;
public Order getOrder() {
return order;
}
public void setOrder(Order order) {
this.order = order;
}
}
10. 共享主键关联样例—映射配置文件
order
11. 共享主键关联样例—摘要
12. 一对一关联—持久化代码片段
package com.oracle.test;
import java.util.Date;
public class TestOnetoOne {
public static void main(String[] args) {
Address addr = new Address();
addr.setCity("上海");
addr.setStreet("南京东路");
addr.setZip("021");
Order order=new Order();
order.setName("order1");
order.setCost(200);
order.setCreatedDate(new Date());
order.setAddr(addr);
addr.setOrder(order);
Configuration cfg = new Configuration().configure();
SessionFactory sf = null;
Session s = null;
Transaction tran = null;
try {
sf = cfg.buildSessionFactory();
s = sf.openSession();
tran = s.beginTransaction();
s.save(order);
tran.commit();
} catch (HibernateException e) {
e.printStackTrace();
tran.rollback();
}finally{
if(s!=null){s.close();}if(sf!=null){sf.close();}
}
13. cascade属性
a) cascade属性,级联操作,指的是当主控方执行操作时(样例中的Order),关联对象(样例中的Address)是否执行同步操作,如主控方执行save-update或delete方法时,是否同时对关联对象执行save-update或delete
b) cascade属性可选值:
none:所有情况下均不进行级联
save-update:在执行save-update时进行级联操作
delete:在执行delete时进行级联操作
all:所有情况下均进行级联操作
14. outer-join属性
a) outer-join属性,级联对象加载策略,指的是当主控方被加载时(样例中的Order),关联对象(样例中的Address)是以一个left outer join关联SQL语句加载还是另外使用一个单独的查询SQL加载。
b) select {……} from t_order left outer join t_address on order.id=addr.id where order.id=?
c) select {…} from t_order where id=?;select {…} from t_address where order_id=?
d) outer-join属性可选值:
true:总是使用outer-join
false:不使用outer-join
auto:如果关联对象没有采用Proxy机制,则使用outer-join
1. 一对多关联是应用最广泛的关联,一对多关联包括两种形式:
单向一对多关联
双向一对多关联
2. 一对多关联—数据模型
3. 单向一对多关联—POJO类片段
public class Order {
private Integer Id;
private String name;
private Integer cost;
private Date createdDate;
private Set- items;
……
}
public class Item {
private Integer Id;
private String name;
private Double cost;
private Integer amount;
……
}
4. 单向一对多关联—映射配置
5. 一对多关联样例—摘要
6. 单向一对多关联—持久化代码片段
package com.oracle.test;
public class TestOnetoMany {
public static void main(String[] args) {
Set- items=new HashSet
- ();
Item item1 = new Item();
item1.setName("item1");
item1.setAmount(1);
item1.setCost(12.5);
items.add(item1);
Item item2 = new Item();
item2.setName("item2");
item2.setAmount(1);
item2.setCost(13.8);
items.add(item2);
Order order=new Order();
order.setName("order1");
order.setCost(200);
order.setItems(items);
Configuration cfg = new Configuration().configure();
SessionFactory sf = null;
Session s = null;
Transaction tran = null;
try {
sf = cfg.buildSessionFactory();
s = sf.openSession();
tran = s.beginTransaction();
s.save(order);
tran.commit();
} catch (HibernateException e) {
e.printStackTrace();
tran.rollback();
}finally{
if(s!=null){s.close();}if(sf!=null){sf.close();}
}
7. 双向一对多关联—POJO类片段
package com.oracle.entity;
import java.util.Date;
import java.util.Set;
public class Order {
private Integer Id;
private String name;
private Integer cost;
private Date createdDate;
private Set- items;
public Set
- getItems() {
return items;
}
public void setItems(Set
- items) {
this.items = items;
}
package com.oracle.entity;
public class Item {
private Integer Id;
private String name;
private Double cost;
private Integer amount;
private Order order;
public Order getOrder() {
return order;
}
public void setOrder(Order order) {
this.order = order;
}
}
8. 双向一对多关联—映射配置
9. 双向一对多关联样例—摘要
10. 双向一对多关联—持久化代码片段
package com.oracle.test;
public class TestOnetoMany {
public static void main(String[] args) {
Set- items=new HashSet
- ();
Item item1 = new Item();
item1.setName("item1");
item1.setAmount(1);
item1.setCost(12.5);
items.add(item1);
Item item2 = new Item();
item2.setName("item2");
item2.setAmount(1);
item2.setCost(13.8);
items.add(item2);
Order order=new Order();
order.setName("order1");
order.setCost(200);
item1.setOrder(order);
item2.setOrder(order);
order.setItems(items);
Configuration cfg = new Configuration().configure();
SessionFactory sf = null;
Session s = null;
Transaction tran = null;
try {
sf = cfg.buildSessionFactory();
s = sf.openSession();
tran = s.beginTransaction();
s.save(order);
tran.commit();
} catch (HibernateException e) {
e.printStackTrace();
tran.rollback();
}finally{
if(s!=null){s.close();}if(sf!=null){sf.close();}
}
11. inverse属性
a) inverse属性,反转,用来指定关联关系的方向,指定由谁来负责关系的维护,inverse=false的一方负责关系的维护
b) one-to-many关系中,将many一方设为关系维护方(inverse=false),有助于性能的改善
12. lazy属性
a) lazy属性,延迟加载,即是否把主控方属性及关联对象一次性加载到内存中,lazy=false,不立即加载,等到用时再去数据库加载关联对象,lazy=true,立即加载关联对象
b) session关闭后再去加载关联对象,会报异常
1. 多对多关联
a) 多对多关联是最复杂的一个关联
b) 表示这一信息的最好方式是通过中间的关联类
c) 在Hibernate中,可以这个关联类映射为实体,任何一端映射两个一对多的关联
2. 多对多关联—数据模型
3. 多对多关联样例—POJO类片段
package com.oracle.entity;
public class Student {
private Integer Id;
private String name;
private String sex;
private Date birthday;
private Set courses=new HashSet();
public Set getCourses() {
return courses;
}
public void setCourses(Set courses) {
this.courses = courses;
}
public void addCourse(Course c){
this.courses.add(c);
c.addStudent(this);
}
}
package com.oracle.entity;
public class Course {
private Integer Id;
private String name;
private String description;
private Set students=new HashSet();
public Set getStudents() {
return students;
}
public void setStudents(Set students) {
this.students = students;
}
public void addStudent(Student s){
this.students.add(s);
}
}
4. 多对多关联样例—映射文件配置
5. 多对多关联样例—摘要
6. 多对多关联—持久化代码片段
public class TestManytoMany {
public static void main(String[] args) {
Course c1=new Course();
c1.setName("corejava");
c1.setDescription("java 语言基础!");
Course c2=new Course();
c2.setName("jdbc");
c2.setDescription("java 连接数据库!");
Student s1=new Student();
s1.setName("rose");
s1.addCourse(c1);
Student s2=new Student();
s2.setName("jack");
s2.addCourse(c1);
s2.addCourse(c2);
Configuration cfg = new Configuration().configure();
SessionFactory sf = null;
Session s = null;
Transaction tran = null;
try {
sf = cfg.buildSessionFactory();
s = sf.openSession();
tran = s.beginTransaction();
s.save(s1);
s.save(s2);
tran.commit();
} catch (HibernateException e) {
e.printStackTrace();
tran.rollback();
}finally{
if(s!=null){s.close();}if(sf!=null){sf.close();}
}
}
}
一对一关联
唯一外键/共享主键
cascade/outer-join
一对多关联
单向/双向
inverse/lazy
多对多关联
中间表
e-learning系统部分功能持久化实现
教师(T)、学生(S)、课程(C)
s:c=m:n
c:t=1:m
控制台出现课程列表(包括任课老师,已选学员人数),输入学生信息进行课程选择,相应的把最新课程列表展示出来。