`

Hibernate(十五):用Hibernate求记录总数的一个怪胎

阅读更多

     项目中求满足某一条件记录数是这样来的: super.getHibernateTemplate().findByCriteria(d).size(). 有些怪. 由于对接口编程与hibernate也多少有些了解,以学习的心态首先想到的是,可能hibernate方法findByCriteria的是一List 的非ArrayList实现类,也就是hibernate自身的一个特定功能的list实现类, 而再在调用size方法时,那个实现类实际上是执行了类似count(*)那样的SQL.

    有了这样的假想后, 心里老放着也不是个事, 验证下吧. 于是在IDE里设置断点,调用.

    出现了如下图所示的情况:

 

   

    findByCriteria方法返回的results不是什么高级特定功能的list实现类, 也就是平常的ArrayList! 这还了得!从图中也能到, 返回值的size是3008! 下面的值能看到一个一个的Node实例. 这样也就是说, findByCriteria后再size的策略就是把所有满足条件的所有数据库记录转为java对象加载到JVM内存中. 费了这么大的事,又占了这么多的内存空间,就为了看这些记录的个数!

    顺着上面的思路, 再有些夸张地打个比方: 国家为了搞人口普查,也想不到什么好的办法(或者说领导由于某些原因压根就没想),于是一拍脑袋,让全国的人来下数数不就得了. 于是间,火车、汽车、飞机、船等交通工具都塞满了人,他们有一个目的地--首都,也为了一个目标,让国家有关部门数一数人数..... 数完了, 那你们还回去干手里的活吧.

    有些搞笑了.

    凡事都是有些它存在的原因的,顺着这个想法下来: 这种方法有什么好处? 现在能想到的一个就是,findByCriteria后再size的策略提供了一种统一的方法.这样就可以写到父类里,供子类孙类调用,也就是说在代码实现上有优势.

    那有没有可能以效率高的运行方式--也就是很容易想到的count(*)--来做到代码上比较通用的实现呢? 抛砖引玉,希望能得到大家的指点.

  • 大小: 34.8 KB
分享到:
评论
8 楼 duduli 2009-04-08  
确实用list去求size是个很占用空间的问题。
   更青睐count
7 楼 qxhzzz 2009-04-08  
wang19841229 写道
Hibernate中的list的size()方法压根就不是用来做数据总数汇总的,真正的汇总应当使用HQL或者QBC等查询语句调用相应的汇总函数,交由数据库来实现而不能把计算数据总数的任务交个程序把数据一次性的查出了来,
正解list的size()方法是List的方法和Hibernate没有关系,当然也可以用它来做数据总数的汇总。
在criteria中做数据总汇一般是
criteria.setProjection(Projections.rowCount());
		return (Integer) hibernateTemplate.execute(new HibernateCallback() {

			public Object doInHibernate(Session session)
					throws HibernateException, SQLException {
				return criteria.getExecutableCriteria(session).uniqueResult();
			}
		});

注意Projections.rowCount(),代码应该还能再简化
6 楼 rmn190 2009-04-08  
daquan198163 写道
d.setProjection(Projections.countDistinct("id"));
List list = this.findByCriteria(d);
int result = 0;
for (Iterator it = list.iterator(); it.hasNext();) {
Integer item = (Integer) it.next();
result += item;
}
return result;



谢谢daquan198163, 看你了的解法, 我想通了些: super.getHibernateTemplate().findByCriteria(d)这样的写法是可以得到汇总信息的.

但findByCriteria后list方法还是显的有些不伦不类.

------------

前进了一步,  可以基于daquan198163的写法写一通用的求汇总信息的父类方法.
5 楼 daquan198163 2009-04-08  
d.setProjection(Projections.countDistinct("id"));
List list = this.findByCriteria(d);
int result = 0;
for (Iterator it = list.iterator(); it.hasNext();) {
Integer item = (Integer) it.next();
result += item;
}
return result;
4 楼 rmn190 2009-04-08  
yidao620c 写道
为什么要用红色遮起来呢?这个属于商业机密麽


呵呵, 不算什么商业机密,但从那一团红色自能看出我现在的公司以及现在的项目,为了避免可能的麻烦就用红色涂了起来.

麻烦还是少惹些为好啦.
3 楼 yidao620c 2009-04-08  
为什么要用红色遮起来呢?这个属于商业机密麽
2 楼 wang19841229 2009-04-08  
估计Hibernate中的list的size()方法压根就不是用来做数据总数汇总的,真正的汇总应当使用HQL或者QBC等查询语句调用相应的汇总函数,交由数据库来实现而不能把计算数据总数的任务交个程序把数据一次性的查出了来,在调用list的size()方法。这么做即使你不使用list的size方法,也是一次性的把数据全部加载到内存中。
所以如果业务上确实需要获得查询的总数,应当使用相应的汇总函数把数据汇总的任务交给DB来解决。
这只是我的个人观点!拍砖
1 楼 ray_linn 2009-04-07  
为什么不直接在HQL里用count?

相关推荐

    org.hibernate.HibernateException: No Hibernate Session bound to thread

    在 Java web 开发中, Hibernate 是一个非常流行的 ORM(Object-Relational Mapping)框架,用于将 Java 对象映射到关系数据库中。然而,在使用 Hibernate 进行数据库操作时,经常会遇到 "No Hibernate Session ...

    hibernate-release-5.2.13.Final 官网

    官网hibernate:问题说明: 1、安装整合通过; 2、整合时注意javassist-3.22.0-GA.jar与struts2.4的 javassist-3.20.0-GA.jar重复...3、整合所需基础包以及整合需要的外部包,自己放到一个新建文件夹中,方便大家查找!

    hibernate jar包:hibernate-commons-annotations-4.0.1.Final.jar等

    Hibernate.jar包,Hibernate可以应用在任何使用JDBC的场合,包含 hibernate-commons-annotations-4.0.1.Final.jar hibernate-core-4.1.12.Final.jar hibernate-ehcache-4.1.12.Final.jar hibernate-entitymanager-...

    hibernate-memcached包

    **hibernate-memcached包** 是一个专为Hibernate框架设计的扩展,目的是将流行的分布式内存缓存系统Memcached整合到Hibernate中,作为其二级缓存解决方案。在大型分布式应用中,缓存技术是提高性能的关键,特别是...

    hibernate_5.1包

    hibernate-swarmcache:支持SwarmCache,一个简单而功能强大的分布式缓存机制。它使用IP组播来有效地在缓存的实例之间进行通信。它是快速提高集群式Web应用程序的性能的理想选择。 hibernate-proxool:支持Proxool...

    hibernate-validator 5.3.5.Final jar

    hibernate-validator 5.3.5.Final jar包 ;desc:if you want validator your project

    DmDialect-for-hibernate4.0.zip

    Hibernate是一个强大的ORM(对象关系映射)框架,它允许开发者用面向对象的方式处理数据库,将Java对象与数据库表之间的映射关系自动化。Dialect在Hibernate中起着至关重要的作用,它定义了特定数据库的SQL语法、...

    Hibernate3.1_学习源码

    04 04Hibernate_Composite : 复合主键的使用,在开发中很少用到,一般良好的设计都会为一个表添加一个自动增长的主键标识列。其中重点配置方法和Hibernate中普遍采用的方法链编程的使用。还需注意可以将组合主键构建...

    Hibernate-Extension Middlegen-Hibernate

    首先,Hibernate是Java平台上的一个开源ORM框架,它允许开发者用面向对象的方式来操作数据库,从而降低了数据库编程的复杂性。通过Hibernate,开发者可以避免编写大量的JDBC代码,只需定义对象的属性和关系,就能...

    hibernate的第一个例子

    **标签关键词:“hibernate”**:Hibernate是一个流行的Java ORM(对象关系映射)框架,它允许开发者使用面向对象的方式来操作数据库,避免了直接编写SQL语句的繁琐工作。 **详细知识点讲解:** 1. **Hibernate ...

    hibernate2.1相关jar包

    请注意,Hibernate 2.1是一个较旧的版本,现代开发中通常使用更先进的Hibernate 5.x或更高版本,它们提供了更多的特性、优化和对新Java及JPA标准的支持。尽管如此,理解Hibernate 2.1的基本工作原理对于学习ORM框架...

    kingbaseV8 hibernate jdbc 驱动

    Hibernate是一个优秀的对象关系映射(ORM)框架,它简化了Java应用程序对数据库的操作,通过将Java对象与数据库表进行映射,开发者可以避免直接编写SQL语句,提高了开发效率。在标题和描述中提到的"kingbaseV8 ...

    hibernate第一个hibernate

    《Hibernate入门:初识与实践》 ...总之,"hibernate第一个hibernate"项目是一个绝佳的起点,它将引导你了解并掌握Hibernate的基本概念和操作。通过实践,你可以逐步熟悉ORM思想,为后续的Java开发奠定坚实的基础。

    spring+hibernate整合实现简单数据库添加记录

    每个实体类通常对应一个Hibernate的.hbm.xml映射文件,或者使用JPA的@Entity注解和注解驱动配置。 4. **DAO层**:定义数据访问对象(DAO),这些对象将处理与数据库的交互。在Spring中,我们可以使用DAO接口,然后...

    hibernate基础jar包

    1. Hibernate ORM框架:Hibernate是一个流行的Java ORM框架,它通过XML或注解的方式将Java对象与数据库表进行映射,使得开发者无需编写大量的SQL语句,就能完成对数据库的操作。它支持多种数据库,如MySQL、Oracle、...

    hibernate-validator-6.0.18.Final-sources.jar

    java运行依赖jar包

    精通Hibernate:Java对象持久化技术详解.pdf

    《精通Hibernate:Java对象持久化技术详解》这本书深入剖析了Hibernate这一流行的Java对象关系映射(ORM)框架,旨在帮助开发者全面理解并熟练掌握Hibernate的使用。Hibernate是Java开发中的重要工具,它简化了...

    hibernate4.jar

    本文将详细探讨hibernate4.jar的核心功能,以及如何利用它来构建一个完整的Hibernate框架。 首先,`hibernate4.jar`是Hibernate 4版本的基础库文件,包含了运行Hibernate应用程序所必需的类和接口。这个JAR文件包含...

    hibernate所需包:hibernate3,依赖包,JDBC

    Hibernate是一个流行的Java持久化框架,它简化了数据库操作,使得开发者可以通过对象关系映射(ORM)技术来处理数据库交互。 **Hibernate ORM框架** Hibernate3是Hibernate的第三个主要版本,发布于2005年,它提供...

    hibernate中五个核心接口

    Session 接口是 Hibernate 中最常用的一个接口,它是执行 CRUD(Create、Read、Update、Delete)操作的主要工具。Session 提供了多种操作数据库的方法,包括保存对象、查询对象、更新对象以及删除对象等。 **特点:...

Global site tag (gtag.js) - Google Analytics