请参考:http://1194867672-qq-com.iteye.com/blog/1730513
下面根据经验谈谈Hibernate的一对多,多对一问题。
可参考:http://blog.csdn.net/lxl_family/article/details/26523757
双向一对多关系,一是关系维护端(owner side),多是关系被维护端(inverse side)。数据库中的表一般都是相互关联的,它们通过foreign key产生关系。在关系被维护端需要通过@JoinColumn建立外键列指向关系维护端的主键列。
@Entity //设置一个类为实体类</span> @JsonIgnoreProperties(value={"orderItems "}) </span> @Table(name="Order") //作用:设置实体类对应的表,常与@Entity一起使用</span> public class Order implements Serializable { @Id @GeneratedValue(strategy=GenerationType.IDENTITY) private Long id; @JsonIgnore @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") private transient String strbegin; @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")</span> private Date begindate; private Set<OrderItem> orderItems = new HashSet<OrderItem>(); 。。。。 @OneToMany(mappedBy="order",cascade = CascadeType.ALL, fetch = FetchType.LAZY) @OrderBy(value = "id ASC") public Set<OrderItem> getOrderItems() { return orderItems; } //其他get set方法省略 } public class OrderItem implements Serializable { @Id @GeneratedValue(strategy=GenerationType.IDENTITY) private Long id; private String itenName; private Order order; //不用再根据表结构定义order_id属性 。。。。 @ManyToOne(cascade=CascadeType.REMOVE,optional=false) @JoinColumn(name = "order_id",referencedColumnName="id") //OrderItem表中的order_id字段与order表中的id关联 public Order getOrder() { return order; } }
@JsonIgnore 也可以直接在属性上Ignore
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss") 对属性进行格式转换,一般用于时间等特殊格式。
如果不处理,可能报错:
jackson.databind.ser.BeanSerializer.serialize(BeanSerializer.java:143) //Json转换死循环
org.springframework.orm.hibernate3.HibernateQueryException: could not resolve property
org.springframework.http.converter.HttpMessageNotWritableException: Could not write content: could not initialize proxy - no Session (through reference chain。。。)
1、从One的一方关联到Many的一方:
查找出球员所属的球队,可以使用以下语句:
SELECT DISTINCT t FROM Order t JOIN t.OrderItems p where p.ItemName LIKE :name或者使用以下语句:
SELECT DISTINCT t FROM Order t,IN(t.OrderItems) p WHERE p.ItemName LIKE :name
select distinct Order0_.id as id0_, Order0_.ItemName as ItemName0_ from Order Order0_ inner join player OrderItem1_ on Order0_.id=OrderItem1_.Order_id where OrderItems1_.ItemName like ?
不能使用以下语句:
<span style="font-size:12px;">SELECT DISTINCT t FROM Order t WHERE t.OrderItem.ItemName LIKE :ItemName </span>
不能使用t.OrderItems.ItenName这样的方式从集合中取值,要使用join或者in才行。
2、从Many的一方关联到One的一方:
查找出某个球队下的所有球员,可以使用以下查询语句:
<span style="font-size:12px;">SELECT p FROM OrderItem p JOIN p.Order t WHERE t.id = :id </span>
SELECT p FROM OrderItem p, IN(p.Order) t WHERE t.id = :id这两条查询语句是等价的,产生的SQL语句如下:(产生了两条SQL)
Hibernate: select OrderItem0_.id as id1_, OrderItem0_.ItemName as ItemName1_, OrderItem0_.Order_id as Order3_1_ from OrderItem OrderItem0_ inner join Order Order1_ on OrderItem0_.Order_id=Order1_.id where Order1_.id=? Hibernate: select Order0_.id as id2_0_, Order0_.ItemName as ItemName2_0_ from Order Order0_ where Order0_.id=?
SELECT p FROM OrderItem p WHERE p.Order.id = :id这条语句产生的SQL如下:(产生了两条SQL)
SELECT p FROM OrderItem p WHERE p.Order.id = :id Hibernate: select OrderItem0_.id as id1_, OrderItem0_.name as name1_, OrderItem0_.Order_id as Order3_1_ from OrderItem OrderItem0_ where OrderItem0_.Order_id=? Hibernate: select Order0_.id as id0_0_, Order0_.name as name0_0_ from Order Order0
SELECT p FROM OrderItem p JOIN FETCH p.Order t WHERE t.id = :id
Hibernate: select OrderItem0_.id as id1_0_, Order1_.id as id2_1_, OrderItem0_.name as name1_0_, OrderItem0_.Order_id as Order3_1_0_, Order1_.name as name2_1_ from OrderItem OrderItem0_ inner join Order Order1_ on OrderItem0_.Order_id=Order1_.id where Order1_.id=?