标签:
Hibernate是一种orm技术框架,处于面向对象和数据库的中间层次
一、概述
1. 作为面向对象的思考者,希望的最理想的情况是在使用对象的时候,最少的关注数据库
2. 对象与关系型数据库在领域概念上却又有着天然的不一致
(1)领域概念应对成对象是需要有行为的 (2) 对象的概念在数据的表中不是完全一样的
下面就总结一下对象的关系在数据库中的样子,同时引出Hibernate的几种表达关系注解的使用方式
@OneToOne @OneToMany @ManyToOne @ManyToMany
二、具体
1、对象之间的一对一关系
对象领域:一个对象指向另一个对象的指针
数据库领域: 一个表的外键关联另一个表的主键
我们使用@OneToOne的方式进行一对一关联
@Entity
@Table(name = "orders")
public class Order
{
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private int id;
private String name;
@OneToOne
@JoinColumn(name = "productId")
private Product product;
public Order() {
// TODO Auto-generated constructor stub
}
public Order(String name) {
this.name = name;
}
@Override
public String toString() {
return "Order [id=" + id + ", name=" + name + "]";
}
}
解释:@OneToOne 是关系的标记,@JoinColum是主动定义外键的名称,如果不定义,会默认搜索Product对应的表的名称默认定义为tablename_id
Product的定义
@Entity
@Table(name = "products")
public class Product {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private int id;
private String name;
public Product(String name) {
this.name = name;
}
public Product() {
// TODO Auto-generated constructor stub
}
@Override
public String toString() {
return "Product [name=" + name + "]";
}
}
在这种情况下,对应的数据库表是:

补充:
如果希望在面向对象的领域product也能找到order,就需要在Product类中保存一个指向Order的指针,如果还是用@OneToOne就会在product中额外加一个外键
为了避免数据库再加外键,如何实现呢? 使用mappedBy
//product指的是对方的product属性 @OneToOne(mappedBy = "product") private Order order;
可见 mappedBy的含义是什么呢? 本质是级联处理的维护端是那一方。
关于级联处理理解,下面是对象的依赖关系:
A ---> B --->C
1. A是关系维护者
下面我们可以使用实例来证明一下:
@Test
public void testSaveOrder() {
Order order = new Order("dfp");
Product product = new Product("machine");
order.setProduct(product);
orderdao.save(order);
System.out.println(order.toString());
}
上面的代码,product被设置到了order中,当order被保存到数据库中的时候,是否会同步保存product呢?
如果需要同步保存produt需要将其cascade选项设置为CASCADE.ALL
@OneToOne(cascade = CascadeType.ALL) @JoinColumn(name = "productId") private Product product;
2. 对象之间多对一的关系
最简单的情况: 比如一个商品关联一个品牌
@Entity
@Table(name = "productItems")
public class ProductItem {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private int id;
private String name;
@OneToOne
@JoinColumn(name = "lableName")
private Lable lable;
public ProductItem() {
// TODO Auto-generated constructor stub
}
public ProductItem(String name) {
this.name = name;
}
public void setLable(Lable lable) {
this.lable = lable;
}
@Override
public String toString() {
return "ProductItem [name=" + name + ", lable=" + lable + "]";
}
}
@Entity
@Table(name = "lables")
public class Lable {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private int id;
private String name;
public Lable(String name) {
this.name = name;
}
public Lable() {
// TODO Auto-generated constructor stub
}
@Override
public String toString() {
return "Lable [name=" + name + "]";
}
}

3. 对象之间的一对多的关系(包含反向的多对一)
对象模型: ShoppingCard (1)---- product(n) (那么 ShoppingCard 对应 product 是1对多的关系product 对应 ShoppingCard 是多对一的关系)
数据库模型:
(1) 选取ShoppingCard和product的主键,建立起一个新表ShoppingCards_products

对应的代码如下:
@Entity
@Table(name = "shoppingCards")
public class ShoppingCard {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private int id;
public ShoppingCard() {
// TODO Auto-generated constructor stub
}
@OneToMany(cascade = CascadeType.ALL)
private List<Product> products = new ArrayList<Product>();
public void addProduct(Product product){
products.add(product);
}
}
@Entity
@Table(name = "products")
public class Product {
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private int id;
private String name;
//product指的是对方的product属性
@OneToOne(mappedBy = "product")
private Order order;
public Product(String name) {
this.name = name;
}
public Product() {
// TODO Auto-generated constructor stub
}
@Override
public String toString() {
return "Product [name=" + name + "]";
}
}
(2) product的外键对应的是shoppingcard的主键
建立product的多对一的关联,同时建立外键
@ManyToOne @JoinColumn(name = "shopppingcard") private ShoppingCard card;
建立数据库模型如下

四、多对多的关系
未完待续
作为多年开发的C++程序员,最近在看java的hibernate发现当你需要解决级联级联更新问题的时候,更多的就要思考生命周期的问题的问题了。
标签:
原文地址:http://www.cnblogs.com/Learn-by-doing/p/4634173.html