`
sorphi
  • 浏览: 46543 次
  • 性别: Icon_minigender_1
  • 来自: 北京
文章分类
社区版块
存档分类
最新评论

hibernate的fetch=“subselect"碰上SQLQuery

阅读更多

会变成fetch="select"

 

List<User> users = sesson.createSQLQuery("select {u.*} from user_table u where ...")
                                          .addEntity("u", User.class).list();
for(User u : users){
  Hibernate.initialize(u.getAddresses());
  //just initialize the first entity's collection property,
  // subselect fetch mode will fetch 
  //collection property for all entities in current session.
  break;
}

 观察打印出来的sql:
1.normal sql: select ... from user_table u where ...
2.fetch sql: select ... from address_table a where a.user_id in (?,?,?,...)

fetch sql并非预想中的:select ... from address_table a where a.user_id in (select u.id from user_table u where ...)

 

关于subselect的局限性,GK语焉不详的回答在这里:
http://opensource.atlassian.com/projects/hibernate/browse/HHH-304

结论:
谨慎使用subselect fetch mode,该模式主要是为了防止batch fetch(fetch="select"并设置了相应的batch size)的碎片化,但是使用in语法,值得改进,且某些情况下自动转变成batch fetch。
尽可能使用默认的select fetch mode并合理设置batch fetch size。在主sql已经是分页查询的情况下,subselect fetch mode是没有必要的。在主sql不是分页查询的情况下,估计结果集大小,结果集非常大的情况下,考虑使用subselect fetch。

 

上面这个例子如果非得保持subselect fetch设置,那就按照batch fetch 的方式老老实实的初始化:

 

for(User u : users){
  Hibernate.initialize(u.getAddresses());
}
 



以上仅根据调试结果和hibernate手册,并未研究hibernate源码的具体实现。欢迎指正。

 

另,今天看源码发现是由于CommonLoader出于某种考虑并未覆盖父类的isSubselectLoadingEnabled()所致。

分享到:
评论

相关推荐

    Hibernate笔记

    4. **Query**: 用于执行HQL(Hibernate Query Language)或原生SQL查询。 5. **Lazy Loading**: 惰性加载机制,用于延迟加载关联对象。只有当真正需要访问关联对象时,Hibernate才会发起数据库查询来获取数据。 6. *...

    Hibernate+中文文档

    16.1. 使用SQLQuery 16.1.1. 标量查询(Scalar queries) 16.1.2. 实体查询(Entity queries) 16.1.3. 处理关联和集合类(Handling associations and collections) 16.1.4. 返回多个实体(Returning multiple ...

    Hibernate之数据加载方式

    - **HQL(Hibernate Query Language)**:Hibernate的专用查询语言,类似SQL,但更面向对象,支持复杂的查询条件和结果映射。 - **Criteria API**:提供了一种基于对象的查询方式,更加灵活且类型安全。 - **...

    hibernate3.2中文文档(chm格式)

    16.1. 使用SQLQuery 16.1.1. 标量查询(Scalar queries) 16.1.2. 实体查询(Entity queries) 16.1.3. 处理关联和集合类(Handling associations and collections) 16.1.4. 返回多个实体(Returning multiple ...

    HibernateAPI中文版.chm

    16.1. 使用SQLQuery 16.1.1. 标量查询(Scalar queries) 16.1.2. 实体查询(Entity queries) 16.1.3. 处理关联和集合类(Handling associations and collections) 16.1.4. 返回多个实体(Returning multiple ...

    如何提高hibernate性能

    使用HQL(Hibernate Query Language)或Criteria API进行查询,它们可以更好地利用Hibernate的优化机制,减少与数据库的交互次数。 9. **避免N+1查询问题**: 在关联查询中,确保一次获取所需的所有关联数据,以...

    Hibernate中文详细学习文档

    16.1. 使用SQLQuery 16.1.1. 标量查询(Scalar queries) 16.1.2. 实体查询(Entity queries) 16.1.3. 处理关联和集合类(Handling associations and collections) 16.1.4. 返回多个实体(Returning multiple ...

    Hibernate_3.2.0_符合Java习惯的关系数据库持久化

    16.1. 使用SQLQuery 16.1.1. 标量查询(Scalar queries) 16.1.2. 实体查询(Entity queries) 16.1.3. 处理关联和集合类(Handling associations and collections) 16.1.4. 返回多个实体(Returning multiple ...

    hibernate 体系结构与配置 参考文档(html)

    使用SQLQuery 16.2. 别名和属性引用 16.3. 命名SQL查询 16.3.1. 使用return-property来明确地指定字段/别名 16.3.2. 使用存储过程来查询 16.3.2.1. 使用存储过程的规则和限制 16.4. 定制SQL用来create,...

    Hibernate 中文 html 帮助文档

    16.1. 使用SQLQuery 16.1.1. 标量查询(Scalar queries) 16.1.2. 实体查询(Entity queries) 16.1.3. 处理关联和集合类(Handling associations and collections) 16.1.4. 返回多个实体(Returning multiple entities)...

    最全Hibernate 参考文档

    16.1. 创建一个基于SQL的Query 16.2. 别名和属性引用 16.3. 命名SQL查询 16.3.1. 使用return-property来明确地指定字段/别名 16.3.2. 使用存储过程来查询 16.3.2.1. 使用存储过程的规则和限制 16.4. 定制SQL用来...

    hibernater调试

    当实体关联的集合未在初始查询中加载,而是在后续访问时触发额外的SELECT语句,这时可以通过调整fetch策略,使用"join fetch"或"subselect fetch"来优化。 另外,优化实体设计也是避免调试问题的重要手段。合理地...

    Hibernate教程

    17.1. 创建一个基于SQL的Query 17.2. 别名和属性引用 17.3. 命名SQL查询 17.3.1. 使用return-property来明确地指定字段/别名 17.3.2. 使用存储过程来查询 17.3.2.1. 使用存储过程的规则和限制 17.4. 定制SQL...

    Hibernate Reference Documentation3.1

    16.1. Using a SQLQuery 16.2. Alias and property references 16.3. Named SQL queries 16.3.1. Using return-property to explicitly specify column/alias names 16.3.2. Using stored procedures for querying ...

    How to solve the hibernate N+1 problem?

    5. **使用`@Fetch(FetchMode.JOIN)`或`@Fetch(FetchMode.SUBSELECT)`**:前者强制使用JOIN来获取关联数据,后者在父对象集合被初始化时执行子查询。 6. **使用`@NamedEntityGraph`**:JPA 2.1引入的新特性,允许...

    hibernate3.04中文文档.chm

    17.1. 创建一个基于SQL的Query 17.2. 别名和属性引用 17.3. 命名SQL查询 17.3.1. 使用return-property来明确地指定字段/别名 17.3.2. 使用存储过程来查询 17.3.2.1. 使用存储过程的规则和限制 17.4. 定制SQL...

    Hibernate3+中文参考文档

    16.1. 创建一个基于SQL的Query 16.2. 别名和属性引用 16.3. 命名SQL查询 16.3.1. 使用return-property来明确地指定字段/别名 16.3.2. 使用存储过程来查询 16.3.2.1. 使用存储过程的规则和限制 16.4. 定制SQL用来...

    hibernate 框架详解

    创建一个基于SQL的Query 17.2. 别名和属性引用 17.3. 命名SQL查询 17.3.1. 使用return-property来明确地指定字段/别名 17.3.2. 使用存储过程来查询 17.3.2.1. 使用存储过程的规则和限制 17.4. 定制SQL用来...

    Hibernate参考文档

    16.1. 使用SQLQuery 16.1.1. 标量查询(Scalar queries) 16.1.2. 实体查询(Entity queries) 16.1.3. 处理关联和集合类(Handling associations and collections) 16.1.4. 返回多个实体(Returning multiple entities)...

Global site tag (gtag.js) - Google Analytics