Hibernate @LazyCollection注释的用途是什么?

时间:2012-10-17 06:29:33

标签: java performance hibernate orm lazy-loading

我有2个实体作为Parent和Child作为OneToMany关系

@Entity
public class Parent {

@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Integer id;

private String name;

@OneToMany(mappedBy = "parent", fetch = FetchType.LAZY)
@IndexColumn(name = "index", base = 1)
@Cascade(org.hibernate.annotations.CascadeType.ALL)
@LazyCollection(LazyCollectionOption.EXTRA)
private List<Child> childs = new ArrayList<Child>();
// getter and setter

}

所以这里有什么用于 @LazyCollection(LazyCollectionOption.EXTRA),它什么时候会出现在图片中,比如哪个带有子列表的操作,这将是有益的?

3 个答案:

答案 0 :(得分:28)

EXTRA = .size()和.contains()不会初始化整个集合

TRUE =在首次访问时初始化整个集合

FALSE =预先加载

答案 1 :(得分:17)

  

这是一个非常好的问题,因此我决定将此答案转换为article as well

实际上没有理由使用@LazyCollection

不需要TRUEFALSE值,因为使用JPA FetchType.LAZYFetchType.EAGER可以获得相同的行为。

EXTRA值在JPA中没有等效值,专为非常大的集合而设计。当您第一次访问EXTRA惰性集合时,该集合未完全加载,因为任何JPA集合通常都是如此。

相反,使用辅助SELECT逐个提取每个元素。这可能听起来像是一种优化,但并不是因为EXTRA懒惰的集合容易出现N+1 query issues

请注意,这仅适用于带有List@OrderColumn(s)注释的有序集合,Map(s)。对于行李(例如,不保留任何特定排序的实体的常规List),@LazyCollection( LazyCollectionOption.EXTRA )的行为就像任何其他LAZY集合一样(集合在被访问时完全取出)第一次)。

如果你有一个非常大的集合,那么你根本不应该映射它。相反,您应该只映射@ManyToOne侧,而不是父级集合,您应该使用分页的JPQL查询。

JPQL查询更容易调整,因为您可以应用任何过滤条件,并且可以对结果集进行分页。

答案 2 :(得分:8)

为了给你一个提示,主要是出于性能原因,你可以开始阅读以下链接:

Second Level Cache

Hibernate Documentation