`
foryougeljh
  • 浏览: 116382 次
  • 性别: Icon_minigender_1
  • 来自: 上海
社区版块
存档分类
最新评论

Hibernate - DetachedCriteria 的完整用法

 
阅读更多

http://blog.csdn.net/kjfcpua/article/details/4287248

Hibernate 设计了 CriteriaSpecification 作为 Criteria 的父接口,下面提供了 Criteria和DetachedCriteria 。Criteria 和 DetachedCriteria 的主要区别在于创建的形式不一样, Criteria 是在线的,所以它是由 Hibernate Session 进行创建的;而 DetachedCriteria 是离线的创建时无需Session

DetachedCriteria 提供了 2 个静态方法 forClass(Class) 或 forEntityName(Name)进行DetachedCriteria 实例的创建。


Spring的框架提供了getHibernateTemplate().findByCriteria(detachedCriteria)方法可以很方便地根据DetachedCriteria来返回查询结果。

Criteria和DetachedCriteria均可使用
Criterion[规范]和Projection[投影]设置查询条件。可以设置FetchMode(联合查询抓取的模式),设置排序方式。对于Criteria还可以设置 FlushModel(冲刷Session的方式)和LockMode(数据库锁模式)

下面对Criterion和Projection进行详细说明。
Criterion是Criteria的查询条件。Criteria提供了add(Criterion criterion)方法来添加查询条件
Criterion接口的主要实现包括:Example 、Junction和SimpleExpression 。而Junction 的实际使用是它的两个子类
conjunction[联合(and)]和disjunction[分离(or)],分别是使用AND和OR操作符进行来联结查询条件集合(Restrictions创建)。

Criterion的实例可以通过
Restrictions[约束]工具类来创建,Restrictions 提供了大量的静态方法,
如eq(等于)、ge(大于等于)、between 等来方法的创建 Criterion 查询条件(SimpleExpression 实例)。除此之外,Restrictions还提供了方法来创建conjunction和disjunction 实例,通过该实例的add(Criteria)方法来增加查询条件形成一个查询条件集合

至于Example的创建有所不同,Example本身提供了一个静态方法create(Object entity),即根据一个对象(实际使用中一般是映射到数据库的对象)来创建。然后可以设置一些过滤条件:
Example exampleUser =Example.create(u)
.ignoreCase() // 忽略大小写
.enableLike(MatchMode.ANYWHERE);// 对 String 类型的属性,无论在那里值在那里都匹配。相当于%value%

Project主要是让Criteria能够进行报表查询,并可以实现分组。Project 主要有SimpleProjection、ProjectionList 和Property三个实现。其中 SimpleProjection和ProjectionList的实例化是由内建的 Projections 来完成,如提供的 avg、count、max、min、sum 可以让开发者很容易对某个字段进行统计查询

Property 是对某个字段进行查询条件的设置
如通过Porperty.forName("color").in(new String[]{"black","red","write"});则可以创建一个 Project 实例。
通过criteria的add(Project)方法加入到查询条件中去

使用 Criteria 进行查询,主要要清晰的是 Hibernate 提供了那些类和方法来满足开发中查
询条件的创建和组装,下面介绍几种用法:

1. 创建一个Criteria实例
org.hibernate.Criteria接口表示特定持久类的一个查询。Session是Criteria实例的工厂。
Criteria crit = sess.createCriteria(Cat.class);
crit.setMaxResults(50);
List cats = crit.list();

2. 限制结果集内容
一个单独的查询条件是org.hibernate.criterion.Criterion 接口的一个实例
org.hibernate.criterion.Restrictions类 定义了获得某些内置Criterion类型的工厂方法
List cats = sess.createCriteria(Cat.class)
.add( Restrictions.like("name", "Fritz%") )
.add( Restrictions.between("weight", minWeight, maxWeight) )
.list();
约束可以按逻辑分组
List cats = sess.createCriteria(Cat.class)
.add( Restrictions.like("name", "Fritz%") )
.add( Restrictions.or(
Restrictions.eq( "age", new Integer(0) ),
Restrictions.isNull("age")
))
.list();

List cats = sess.createCriteria(Cat.class)
.add( Restrictions.in( "name", new String[] { "Fritz", "Izi", "Pk" } ) )
.add( Restrictions.disjunction()
.add( Restrictions.isNull("age") )
.add( Restrictions.eq("age", new Integer(0) ) )
.add( Restrictions.eq("age", new Integer(1) ) )
.add( Restrictions.eq("age", new Integer(2) ) )
))
.list();
Hibernate提供了相当多的内置criterion类型(Restrictions子类), 但是尤其有用的是可以允许你直接使用SQL
List cats = sess.createCriteria(Cat.class)
.add(Restrictions.sql("lower({alias}.name) like lower(?)", "Fritz%",Hibernate.STRING))
.list();
{alias}占位符应当被替换为被查询实体的列别名

Property实例是获得一个条件的另外一种途径。你可以通过调用Property.forName() 创建一个Property
Property age = Property.forName("age");

List cats = sess.createCriteria(Cat.class)
.add( Restrictions.disjunction()
.add( age.isNull() )
.add( age.eq( new Integer(0) ) )
.add( age.eq( new Integer(1) ) )
.add( age.eq( new Integer(2) ) )
))
.add( Property.forName("name").in( new String[] { "Fritz", "Izi", "Pk" } ) )
.list();

3. 结果集排序
你可以使用org.hibernate.criterion.Order来为查询结果排序
List cats = sess.createCriteria(Cat.class)
.add( Restrictions.like("name", "F%")
.addOrder( Order.asc("name") )
.addOrder( Order.desc("age") )
.setMaxResults(50)
.list();

List cats = sess.createCriteria(Cat.class)
.add( Property.forName("name").like("F%") )
.addOrder( Property.forName("name").asc() )
.addOrder( Property.forName("age").desc() )
.setMaxResults(50)
.list();

4. 关联
你可以使用createCriteria()非常容易的在互相关联的实体间建立约束
List cats = sess.createCriteria(Cat.class).add(Restrictions.like("name", "F%")
.createCriteria("kittens").add( Restrictions.like("name", "F%")
.list();

注意第二个 createCriteria()返回一个新的 Criteria实例,该实例引用kittens 集合中的元素。
接下来,替换形态在某些情况下也是很有用的
List cats = sess.createCriteria(Cat.class)
.createAlias("kittens", "kt")
.createAlias("mate", "mt")
.add(Restrictions.eqProperty("kt.name", "mt.name") )
.list();
(createAlias()并不创建一个新的 Criteria实例。)
Cat实例所保存的之前两次查询所返回的kittens集合是 没有被条件预过滤的。如果你希望只获得
符合条件的kittens, 你必须使用returnMaps()
List cats = sess.createCriteria(Cat.class)
.createCriteria("kittens", "kt")
.add( Restrictions.eq("name", "F%") )
.returnMaps()
.list();
Iterator iter = cats.iterator();
while ( iter.hasNext() ) {
Map map = (Map) iter.next();
Cat cat = (Cat) map.get(Criteria.ROOT_ALIAS);
Cat kitten = (Cat) map.get("kt");
}

5. 动态关联抓取
你可以使用setFetchMode()在运行时定义动态关联抓取的语义
List cats = sess.createCriteria(Cat.class)
.add( Restrictions.like("name", "Fritz%") )
.setFetchMode("mate", FetchMode.EAGER)
.setFetchMode("kittens", FetchMode.EAGER)
.list();
这个查询可以通过外连接抓取mate和kittens。

6. 查询示例
org.hibernate.criterion.Example类允许你通过一个给定实例构建一个条件查询
Cat cat = new Cat();
cat.setSex('F');
cat.setColor(Color.BLACK);
List results = session.createCriteria(Cat.class)
.add( Example.create(cat) )
.list();
版本属性、标识符和关联被忽略。默认情况下值为null的属性将被排除。可以自行调整Example使之更实用
Example example = Example.create(cat)
.excludeZeroes() //exclude zero valued properties
.excludeProperty("color") //exclude the property named "color"
.ignoreCase() //perform case insensitive string comparisons
.enableLike(); //use like for string comparisons
List results = session.createCriteria(Cat.class)
.add(example)
.list();
甚至可以使用examples在关联对象上放置条件
List results = session.createCriteria(Cat.class)
.add( Example.create(cat) )
.createCriteria("mate")
.add( Example.create( cat.getMate() ) )
.list();

7. 投影(Projections)、聚合(aggregation)和分组(grouping)
org.hibernate.criterion.Projections是 Projection 的实例工厂。我们通过调用setProjection()应用投影到一个查询
List results = session.createCriteria(Cat.class)
.setProjection( Projections.rowCount() )
.add(Restrictions.eq("color", Color.BLACK))
.list();

List results = session.createCriteria(Cat.class)
.setProjection(Projections.projectionList()
.add(Projections.rowCount() )
.add(Projections.avg("weight") )
.add(Projections.max("weight") )
.add(Projections.groupProperty("color") )
)
.list();

在一个条件查询中没有必要显式的使用 "group by" 。某些投影类型就是被定义为 分组投影,他们也出现在SQL的group by子句中。可以选择把一个别名指派给一个投影,这样可以使投影值被约束或排序所引用。
下面是两种不同的实现方式:
List results = session.createCriteria(Cat.class)
.setProjection( Projections.alias( Projections.groupProperty("color"), "colr" ) )
.addOrder( Order.asc("colr") )
.list();
List results = session.createCriteria(Cat.class)
.setProjection( Projections.groupProperty("color").as("colr") )
.addOrder( Order.asc("colr") )
.list();

alias()和as()方法简便的将一个投影实例包装到另外一个 别名的Projection实例中。简而言之,
当你添加一个投影到一个投影列表中时 你可以为它指定一个别名:
List results = session.createCriteria(Cat.class)
.setProjection( Projections.projectionList()
.add( Projections.rowCount(), "catCountByColor" )
.add( Projections.avg("weight"), "avgWeight" )
.add( Projections.max("weight"), "maxWeight" )
.add( Projections.groupProperty("color"), "color" )
)
.addOrder( Order.desc("catCountByColor") )
.addOrder( Order.desc("avgWeight") )
.list();

List results = session.createCriteria(Domestic.class, "cat")
.createAlias("kittens", "kit")
.setProjection( Projections.projectionList()
.add( Projections.property("cat.name"), "catName" )
.add( Projections.property("kit.name"), "kitName" )
)
.addOrder( Order.asc("catName") )
.addOrder( Order.asc("kitName") )
.list();

也可以使用Property.forName()来表示投影:
List results = session.createCriteria(Cat.class)
.setProjection( Property.forName("name") )
.add( Property.forName("color").eq(Color.BLACK) )
.list();

List results = session.createCriteria(Cat.class)
.setProjection( Projections.projectionList()
.add( Projections.rowCount().as("catCountByColor") )
.add( Property.forName("weight").avg().as("avgWeight") )
.add( Property.forName("weight").max().as("maxWeight") )
.add( Property.forName("color").group().as("color" )
)
.addOrder( Order.desc("catCountByColor") )
.addOrder( Order.desc("avgWeight") )
.list();

8. 离线(detached)查询和子查询
DetachedCriteria类使你在一个session范围之外创建一个查询,并且可以使用任意的 Session来执行它
DetachedCriteria query = DetachedCriteria.forClass(Cat.class)
.add( Property.forName("sex").eq('F') );
//创建一个Session
Session session = .;
Transaction txn = session.beginTransaction();
List results = query.getExecutableCriteria(session).setMaxResults(100).list();
txn.commit();
session.close();

DetachedCriteria也可以用以表示子查询。条件实例包含子查询可以通过Subqueries或者Property获得
DetachedCriteria avgWeight = DetachedCriteria.forClass(Cat.class)
.setProjection( Property.forName("weight").avg() );
session.createCriteria(Cat.class)
.add(Property.forName("weight).gt(avgWeight) )
.list();

DetachedCriteria weights = DetachedCriteria.forClass(Cat.class)
.setProjection(Property.forName("weight") );
session.createCriteria(Cat.class)
.add( Subqueries.geAll("weight", weights) )
.list();

相互关联的子查询也是有可能的:
DetachedCriteria avgWeightForSex = DetachedCriteria.forClass(Cat.class, "cat2")
.setProjection( Property.forName("weight").avg() )
.add(Property.forName("cat2.sex").eqProperty("cat.sex") );
session.createCriteria(Cat.class, "cat")
.add( Property.forName("weight).gt(avgWeightForSex) )
.list();


分享到:
评论

相关推荐

    Hibernate 使用DetachedCriteria操作

    **Hibernate 框架及其DetachedCriteria...以上就是关于Hibernate中DetachedCriteria的详细介绍,希望对你在理解和使用Hibernate进行数据库操作时有所帮助。在实践中不断探索和实践,你会发现更多使用技巧和优化策略。

    hibernate-release-5.2.3.Final

    Hibernate,作为Java领域中广泛使用的对象关系映射(ORM)框架,为开发者提供了方便的数据持久化解决方案。本文将针对"hibernate-release-5.2.3.Final"这一版本进行深入探讨,帮助读者掌握其核心特性和实际应用。 1...

    hibernate-distribution-3.5.0-Final-dist文档

    本文档集是针对Hibernate 3.5.0-Final版本的详细指南,涵盖了该框架的核心概念、配置、使用方法以及API。由于文档的完整版可能超过了上传限制,这里只包含“documentation”部分,更多内容可以参考作者提供的专辑...

    hibernate-distribution中文帮助手册

    10. **事务处理**:Hibernate支持JTA和JDBC两种事务处理方式,保证数据的一致性和完整性。 11. **关联映射**:包括一对一、一对多、多对一、多对多四种关系映射,通过外键或中间表实现。 12. **懒加载与立即加载**...

    hibernate-release-5.4.17.Final.zip

    2. HQL查询:使用Query接口进行基于Hibernate Query Language的查询,支持复杂条件和关联查询。 3. Criteria查询:提供更加面向对象的查询方式,通过Criteria和DetachedCriteria构建查询条件。 4. 自动更新与延迟...

    Hibernate-3.2-API-EN.rar

    这个压缩包“Hibernate-3.2-API-EN.rar”包含了Hibernate 3.2版本的API文档,是英文版的资料,对于深入理解和使用Hibernate具有重要的参考价值。 一、Hibernate概述 Hibernate作为一种流行的ORM工具,通过提供一种...

    Hibernate-基础联表模板

    使用Criteria API进行联表查询时,可以使用`createCriteria()`和`createAlias()`方法定义关联关系,并通过`setFetchMode()`设置Fetch策略。 10. **查询结果的转换和处理** Hibernate查询的结果可以是单个对象、...

    hibernate-2.0.zip

    本指南将深入探讨Hibernate 2.0的核心特性、配置、使用方法以及与早期版本的差异。 **标签:** - Hibernate:一个强大的ORM框架,通过映射Java对象到数据库表,实现了对象和关系数据之间的转换。 - Hibernate 2.0:...

    hibernate-api

    Transaction接口提供了开始、提交、回滚事务的方法,确保数据的一致性和完整性。 6. **Cache**:为了提高性能,Hibernate提供了缓存机制。一级缓存是每个Session内的缓存,自动管理对象状态;二级缓存则是...

    hibernate-release-4.1.5.SP1.zip

    2. Criteria API高级用法:利用DetachedCriteria构造复杂查询,实现动态SQL。 3. Callback事件:通过监听器机制,在对象生命周期的不同阶段执行特定操作。 4. Native SQL查询:当HQL或Criteria无法满足需求时,可...

    Hibernate-3.2-API-EN.chm中,英文都有

    这个API文档是针对Hibernate 3.2版本,是理解Hibernate核心功能和使用方法的重要参考资料。 **一、Hibernate ORM概述** Hibernate ORM允许开发人员将Java类与数据库表进行映射,从而减少了直接操作SQL的需要。这...

    hibernate-jar

    `hibernate需要jar包10`表明,为了使用Hibernate,除了`hibernate-jar`之外,可能还需要其他的依赖库,如JDBC驱动、日志库、其他ORM相关的辅助库等,这些JAR文件共同构成了完整的工作环境,确保Hibernate能正常工作...

    Hibernate(24): 为什么用DetachedCriteria不能表连接地取数据?

    在Java的持久化框架Hibernate中,DetachedCriteria是一个强大的查询工具,它允许我们在不与Session交互的情况下构建查询条件。然而,DetachedCriteria在处理复杂的关联查询,尤其是涉及到表连接(JOIN)时,可能存在...

    hibernate-sample:示例 Hibernate 项目以显示 Exists 子句的用法

    使用 Hibernate Criteria && DetachedCriteria Queries演示Exists Clause非常简单的项目 安装 git clone https://github.com/RameshRM/hibernate-sample.git 跑步 mvn install 这是一个maven项目,依赖项是 ...

    hibernate程序高手秘笈-英文版

    通过阅读《Hibernate: A Developer's Notebook》这本书,你不仅可以掌握Hibernate的基本用法,还能深入理解其背后的原理,从而在实际项目中更好地利用Hibernate,提升开发效率和代码质量。书中的实战案例和解决方案...

    hibernate5.1.10 依赖jar包

    Hibernate是一个开源的对象关系映射(ORM)框架,它允许开发者使用面向对象的编程方式来操作数据库,极大地简化了Java应用程序中的数据访问层。在给定的"hibernate5.1.10 依赖jar包"中,包含了Hibernate 5.1.10版本...

    DetachedCriteria使用介绍

    ### DetachedCriteria 使用详解 ...以上方法为 `DetachedCriteria` 的使用提供了丰富的功能,使其成为处理各种查询需求的强大工具。通过灵活运用这些方法,你可以构建出满足各种业务场景的复杂查询。

    DetachedCriteria Criteria 使用方法

    ### DetachedCriteria 使用详解 #### 一、背景与概述 在Web开发中,经常会遇到需要根据用户提供的条件进行动态查询的需求。例如,在社交平台中,用户可以设置多种筛选条件来进行高级搜索,这时就需要动态生成SQL...

    hibernate-Criteria

    要创建一个Criteria实例,可以使用`Session`对象的`createCriteria`方法,该方法接收一个参数,即要查询的实体类类型。例如: ```java Criteria crit = sess.createCriteria(Cat.class); ``` 通过设置最大结果数量...

Global site tag (gtag.js) - Google Analytics