资讯专栏INFORMATION COLUMN

Hibernate之DetachedCriteria、Criteria

Moxmi / 3368人阅读

摘要:此时,我们不能在层使用因为它是和绑定的。可以解决这个问题,即在层,程序员使用来构造查询条件,然后将这个作为方法调用参数传递给业务层对象。而业务层对象获得之后,可以在范围内直接构造,进行查询。参考问题十二投影聚合和分组是的实例工厂。

问题九、Hibernate里面如何用Criteria 查询记录数

【问题描述】在工作中,有一个比较复杂的feature使用的是hibernate的Criteria实现的查询,但是PM要求在查询数据前,先告知用户有多少条数据,让用户去选择返回多少条记录。
【解决办法】使用Projections.count("property") 或者 Projections.rowCount()

Criteria c = session.createCriteria(User.class);  
c.setProjection(Projections.rowCount());  
int rows=Integer.parseInt(c.uniqueResult().toString());
s.setProjection(null)  

参考:http://blog.csdn.net/virgoboy...

问题十、Hibernate Criteria Join with 3 Tables
Criteria c = session.createCriteria(Dokument.class, "dokument");
c.createAlias("dokument.role", "role"); // inner join by default
c.createAlias("role.contact", "contact");
c.add(Restrictions.eq("contact.lastName", "Test"));
return c.list();

或者这样:

Criteria c = session.createCriteria(Dokument.class);
c.createAlias("role", "role"); // inner join by default
c.createAlias("role.contact", "contact");
c.add(Restrictions.eq("contact.lastName", "Test"));
return c.list();

如果实体对象中含有OneToMany关联对象的情况,既是实体中含有list或Set等关联实体集合的情况下怎么办呢?
这个还不知道怎么办,呵呵
方法其实是非常简单的:

dc.createAlias("tags", "t");          
dc.add(Restrictions.eq("t.id", tagId));  

其中tags是个Set,但是想查找属性tags中含有id为tagId的实体,使用上面的就可以了。

这里有一个特殊情况,如果是对引用对象的id查询,则可以不用建立引用,也就是可以不调用createAlias()语句,如下所示:

DetachedCriteria dc = DetachedCriteria.forClass(Student.class);  
dc.add(Restrictions.like("team.id", teamId, MatchMode.ANYWHERE));  

据我个人的经验,team后只能跟其主键属性,比较其他属性要用别名。

参考:http://stackoverflow.com/ques...
http://www.cnblogs.com/newpan...

问题十一、DetachedCriteria、Criteria 使用区别

在常规的Web编程中,有大量的动态条件查询,即用户在网页上面自由选择某些条件,程序根据用户的选择条件,动态生成SQL语句,进行查询。
此时,我们不能在Web层使用Criteria,因为它是和Session绑定的。
DetachedCriteria可以解决这个问题,即在web层,程序员使用DetachedCriteria来构造查询条件,然后将这个 DetachedCriteria作为方法调用参数传递给业务层对象。而业务层对象获得DetachedCriteria之后,可以在session范围内直接构造Criteria,进行查询。就此,查询语句的构造完全被搬离到web层实现,而业务层则只负责完成持久化和查询的封装即可,与查询条件构造完全解耦,非常完美!

Criteria 和 DetachedCriteria 的主要区别
在于创建的形式不一样, Criteria 是在线的,所以它是由 Hibernate Session 进行创建的,而 DetachedCriteria 是离线的,创建时无需Session .
DetachedCriteria的创建

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

Spring 的框架提供了对于离线查询的支持,非常的简单的使用那些方法
Spring 的框架提供了getHibernateTemplate().findByCriteria(detachedCriteria) 方法可以很方便地根据DetachedCriteria 来返回查询结果。Criteria的子类就是 DetachedCriteria 我们可以简单的使用就好了。
使用到了这些我们就不得不说 Restrictions 是产生查询条件的工具类。
当然你也可以手动这么干:

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实例不要去重用它

DetachedCriteria作为子查询
//主查询:人员查询
DetachedCriteria searDc =
DetachedCriteria.forClass(QymlPerson.class);

//子查询:职务人员关系表
DetachedCriteria sub =
DetachedCriteria.forClass(QymlPositionUserLink.class);
sub.add(Restrictions.eq("positionunid", positionunid));
//子查询:指定查询的列(也就是select usernuid from ....)
sub.setProjection(Property.forName("userunid"));

//主查询和子查询关联(也就是where unid in (select userunid from...) )
searDc.add(Property.forName("unid").in(sub));

在上面的例子中,用个一个类似于下面SQL 的子查询

Select * from Person a where a.unid in (select userunid from PositionUserLink b where
b.positionunid = ..)

Property 还有其他的条件判断,参考api
http://docs.jboss.org/hiberna...
ion/Property.html。

动态关联抓取

我们的抓取模式,对于1对多的关联的形式!是不是抓取过来呢?
你可以使用setFetchMode()在运行时定义动态关联抓取的语义

List cats = sess.createCriteria(Cat.class)
    .add( Restrictions.like("name", "Fritz%") )
    .setFetchMode("mate", FetchMode.JOIN)
    .setFetchMode("kittens", FetchMode.JOIN)
    .list();
    

这个查询可以通过外连接抓取mate和kittens。

参考:http://blog.csdn.net/u0128819...
http://blog.sina.com.cn/s/blo...

问题十二、投影(Projections)、聚合(aggregation)和分组(grouping)

org.hibernate.criterion.ProjectionsProjection 的实例工厂。
我们通过调用setProjection()应用投影到一个查询。这个的意思就是查询哪一列的意思
用来进行聚合操作,和sql中的聚合类似.求和/求平均值/统计记录数/…等等.
还有用来获取获取对象的某些属性(表字段)或属性集合.正常情况下,查询返回的是对象或对象的集合.使用投影的话就可以只返回你需要的属性值.此时,即Hibernate不把记录封装对象了,只返回你在投影中设置的属性的值(值的集合)的数组

List results = session.createCriteria(Cat.class)
    .setProjection( Projections.projectionList()
        .add( Projections.rowCount() )
        //当你添加一个投影到一个投影列表中时 你可以为它指定一个别名:如
        //.add( Projections.rowCount() ,"count")
        .add( Projections.avg("weight") )
        .add( Projections.max("weight") )
        .add( Projections.groupProperty("color") )
    )
    .list();

可以选择把一个别名指派给一个投影,这样可以使投影值被约束或排序所引用。下面是两种不同的实现方式:

List results = session.createCriteria(Cat.class)
    .setProjection( Projections.alias( Projections.groupProperty("color"), "colr" ) )
    //.setProjection( Projections.groupProperty("color").as("colr") )
    .addOrder( Order.asc("colr") )
    .list();

也可以使用Property.forName()来表示投影:

List results = session.createCriteria(Cat.class)
    .setProjection( Projections.projectionList()
        .add( Projections.rowCount().as("catCountByColor") )
        .add( Property.forName("name"))
        .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();

参考:http://blog.csdn.net/u0128819...

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/69906.html

相关文章

  • Hibernate4与Spring4集成

    摘要:阿里数据库连接池数据库基本信息配置最大并发连接数初始化连接数量配置获取连接等待超时的时间最小空闲连接数配置间隔多久才进行一次检测,检测需要关闭的空闲连接,单位 1、web.xml openSessionInViewFilter org.springframework.orm.hibernate4.support.OpenSessionInView...

    104828720 评论0 收藏0
  • 利用反射清空hibernate离线查询对象中的所有条件

    摘要:的离线查询对象用起来的确很是方便,但是其有一个缺陷通过条件表达式方法添加的条件会累加其实就是存入中的这样如果要执行不同的查询需要不同的查询条件时就需要分别创建不同的离线查询对象。 hibernate的离线查询对象DetachedCriteria用起来的确很是方便,但是其有一个缺陷:通过·add(条件表达式)方法添加的条件, 会累加, 其实就是存入list中的, 这样如果要执行不同的查...

    Bmob 评论0 收藏0
  • ssh框架整合案例(字典表,no-session,hebiernate|模板的api,懒加载,级联删

    一:字典表 字典信息:在项目中可能会使用到,已经存在的一些信息。 例如,客户的级别:普通用户,vip用户... 客户的来源:网络营销,电话营销... 客户所属行业:电子商务,房地产... 客户的性别:男,女 在保存用户的时候,这些信息都是已经存在的,不应该让用户让用户来任意填写, 而是通过下拉列表来让用户选择。 这些已经存在的信息称之为字典信...

    dkzwm 评论0 收藏0
  • ssh框架整合案例(字典表,no-session,hebiernate|模板的api,懒加载,级联删

    一:字典表 字典信息:在项目中可能会使用到,已经存在的一些信息。 例如,客户的级别:普通用户,vip用户... 客户的来源:网络营销,电话营销... 客户所属行业:电子商务,房地产... 客户的性别:男,女 在保存用户的时候,这些信息都是已经存在的,不应该让用户让用户来任意填写, 而是通过下拉列表来让用户选择。 这些已经存在的信息称之为字典信...

    lufficc 评论0 收藏0

发表评论

0条评论

Moxmi

|高级讲师

TA的文章

阅读更多
最新活动
阅读需要支付1元查看
<