`
kang275284
  • 浏览: 163163 次
  • 性别: Icon_minigender_1
  • 来自: 广州
社区版块
存档分类
最新评论

如何结合hibernate进行复杂的查询功能设计

阅读更多
Hibernate是典型的OPM工具,它将每一个物理表格(Table)映射成为对象(Object),这发挥了面向对象的优势,使设计和开发人员可以从面向对象的角度来进行对数据库的管理。
     在设计到多表操作时,Hibernate提供了与数据库表关系相对应的对象映射关系,一对一、一对多和多对多在这里都可以通过Hibernate的对象映 射关系(Set等)来实现。这为一般情况下的数据库多表操作提供了便捷途径。关于这方面的介绍已经很多,在这里不再复述。
    但是,在有些情况下的多表操作,比如一个统计顾客在2005年的消费总金额的SQL操作如下:
select b.name, count(a.fee) mix(a.chargeBeginTime) max(a.chargeEndTime) from charge a, customer b where a.idCustomer = b.idCustomer and a.chargeBeginTime >= '2005-01-01' and a.chargeEndTime < '2005-12-31' gourp by a.idCustomer
customer表和charge结构如下:

customer表结构:
+------------+-------------+------+-----+---------+-------+
| Field      | Type        | Null | Key | Default | Extra |
+------------+-------------+------+-----+---------+-------+
| IdCustomer | varchar(32) |      | PRI |         |       |
| Name       | varchar(30) |      |     |         |       |
+------------+-------------+------+-----+---------+-------+

charge表结构:
+-----------------+-------------+------+-----+---------+-------+
| Field           | Type        | Null | Key | Default | Extra |
+-----------------+-------------+------+-----+---------+-------+
| IdCharge        | varchar(32) |      | PRI |         |       |
| Fee             | double      | YES  |     | NULL    |       |
| ChargeTimeBegin | datetime    | YES  |     | NULL    |       |
| ChargeTimeEnd   | datetime    | YES  |     | NULL    |       |
+-----------------+-------------+------+-----+---------+-------+

在Hibernate的自带文档中有类似下面的多表查询操作提示:
“select new OjbectC(field1, field2,...) from ObjectA a, ObjectB b ...”,
分析一下可以看出这个操作有两个缺点:
    1) 必须声明并创建类ObjectC,根据Hibernate的特点,需要写一个ObjectC.hbm.xml的PO映射,在只用到创建查询结果的新对象的 时候,这个映射可以是个虚的,即可以没有一个真正的数据库表和ObjectC对应,但是这样的一个虚设的逻辑显然已经违背了Hibernate的思想初 衷;
    2)这个办法只能查询出但条结果记录并只能创建单个的ObjectC对象,这是很局限的,因此在某些情况下根本不能使用(比如本例)。
    所以,对于本例,上面的方法是行不通的。

其实,仔细看看Hibernate的API,就会发现这个问题很好解决。在net.sf.hibernate包中有下面三个对我们很有用的接口:

1、Interface ScrollableResults
    这个接口类似JDBC中的ResultSet一样,提供了对返回结果集合的遍历和字段访问方法,如:
    public boolean next()    游标后移
    public boolean previous() 游标前移
    public boolean scroll(int i) 游标移动到指定未知
    public void beforeFirst() 游标在首记录前
    public void afterLast() 游标在末记录后
    public Object[] get() 将当前记录的字段值以Object对象数组形式返回
    public Object get(int i) 将当前记录的特定字段值以Object对象形式返回
    public Integer getInteger(int col) 将当前记录的特定字段值以Integer对象返回
    public Long getLong(int col) 将当前记录的特定字段值以Long对象返回
    public String getText(int col) 将当前记录的特定字段值以Text对象返回
    public String getString(int col) 将当前记录的特定字段值以String对象返回
    ...等等

2、Interface Query
    Query接口封装了对数据库的查询等操作,在这里,我们使用到它的原因是在于它的scroll()方法可以返回一个ScrollableResults实例:
    public ScrollableResults scroll() 将查询结果以ScrollableResults实例返回,但需要注意的是查询返回的结果其实只是一些id,当需要的时候(比如我们使用 ScrollableResults.next()方法后移游标时)这条需要用到的记录才会被真正初始化(这种技术可以称作:延时初始化)

3、Interface Session
    Session是Hibernate的核心中的核心,通过Session的createQuery()方法,我们能生成一个Query实例:
    public Query createQuery(String queryString) 用给出的HQL查询串创建一个Query实例

好了,了解了上面的三个接口,问题就能够很好的解决了。需要如下几个文件:
Customer.java                            PO对象
Charge.java                                PO对象
TotalCharge.java                        用于保存统计结果Bean
Customer.hbm.xml                      PO映射
Charge.hbm.xml                          PO映射
TotalChargeDao.java                  统计Dao定义
TotalChargeDaoImpl.java           统计Dao定义实现
DaoFactory.java                         Dao工厂
HibernateSessionFactory.java     Session工厂

因 为这里主要讨论的重点是对Customer和Charge的联合查询,所以Customer.java、Charge.java、 Customer.hbm.xml、Charge.hbm.xml四个文件以及TotalChargeDao.java、 DaoFactory.java、HibernateSessionFactory.java的源代码在这里省略掉。

TotalCharge.java 的源代码:
package test.bean;

/**
 *作者:孙星
 **/
public class TotalCharge {
  private String name;
  private Double fee;
  private java.util.Date chargeTimeBegin;
  private java.util.Date chargeTimeEnd;
  public TotalCharge() {
  }

  public String getName() {
    return name;
  }

  public TotalCharge(String name, Double fee, java.util.Date chargeTimeBegin,
                     java.util.Date chargeTimeEnd) {
    this.name = name;
    this.fee = fee;
    this.chargeTimeBegin = chargeTimeBegin;
    this.chargeTimeEnd = chargeTimeEnd;
  }

  public void setName(String name) {
    this.name = name;
  }

  public Double getFee() {
    return fee;
  }

  public void setFee(Double fee) {
    this.fee = fee;
  }

  public java.util.Date getChargeTimeBegin() {
    return chargeTimeBegin;
  }

  public void setChargeTimeBegin(java.util.Date chargeTimeBegin) {
    this.chargeTimeBegin = chargeTimeBegin;
  }

  public java.util.Date getChargeTimeEnd() {
    return chargeTimeEnd;
  }

  public void setChargeTimeEnd(java.util.Date chargeTimeEnd) {
    this.chargeTimeEnd = chargeTimeEnd;
  }
}


TotalChargeDaoImpl.java 代码:
package test.dao.impl;

import java.util.*;
import test.bean.*;
import test.dao.*;
import net.sf.hibernate.*;

/**
 *作者:孙星
 **/
public class TotalChargeDaoImple extends TotalChargeDao{
    
    //下面方法集成自TotalChargeDao
    public List statTotalCharge(Date statTimeBegin, Date statTimeEnd) throws DaoException{
        List res = new Vector();//将用于存放保存的结果集合
        Session session = null;
        ScrollableResults srs = null;
        try{
            session = HibernateSessionFactory.openSession();//得到一个Hibernate Session
            //下面创建一个匿名Query实例并调用它的scroll()方法返回以ScrollableResults形式组织的查询结果
            srs = session.createQuery(“select b.name, count(a.fee) mix(a.chargeBeginTime) max(a.chargeEndTime) from charge a, customer b where a.idCustomer = b.idCustomer and a.chargeBeginTime >= ? and a.chargeEndTime < ? gourp by a.idCustomer“).setDate(0, statTimeBegin).setDate(1, statTimeEnd).scroll();
            //将查询结果放入List保存
            while(srs.next()){
                res.add(new TotalCharge(srs.getString(0), srs,getDouble(1), srs.getDate(2), srs.getDate(3)));
            }
        }catch(HibernateException he){
            ;//loging err.....
            if(srs!=null){
                try{
                    srs.close();
                }catch(Exception e){
                    ;
                }
            }
        }finally{
            try{
                session.close();
            }catch(Exception e){
                ;
            }
        }
        return res;
    }
}
 
分享到:
评论

相关推荐

    招投标系统需求(附创建表语句spring+springmvc+hibernate)源码java毕业设计

    在线招标系统采用spring,spring mvc框架进行开发,数据库方面由于业务不是太复杂,所以使用了hibernate框架。 该毕业设计主要是将招标投标信息公示出来,系统功能包括:招标公示,投标公示,招标发布,服务商管理等...

    源码基于JSP的博客系统(struts+hibernate+spring).rar

    它包含用于构建一个功能齐全的博客系统的源代码和资源文件,结合了Java Server Pages (JSP)、Apache Struts框架、Hibernate持久化框架以及Spring框架的强大功能,以支持高效的数据库操作和灵活的业务逻辑处理。...

    图书管理系统(struts+hibernate+spring+ext).rar

    Hibernate作为持久层框架,负责实现对象关系映射(ORM),将Java对象与数据库表进行映射,简化了数据库操作的复杂性。Spring作为IoC容器,负责管理对象的生命周期和依赖关系,降低了系统各模块之间的耦合度。Ext作为...

    图书管理系统(struts+hibernate+spring)130225.rar

    "图书管理系统(struts+hibernate+spring)130225.rar" 是一个针对计算机专业学生、教师以及图书馆管理员设计的基于Java服务器页面(JSP)的应用程序源码包。该资料包采用了Struts框架来管理Web层的请求与响应,...

    基于JSP的儿童健康保健系统毕业设计论文

    本设计就是基于J2EE 体系结构下的WEB 开发,设计的目的是了解J2EE体系的多层结构以及其两大容器WEB容器和EJB容器,重点掌握WEB技术、Struts和Hibernate技术、熟悉其开发环境的构建和工具的使用。在开发中使用了目前...

    车辆管理系统(struts+hibernate+spring+oracle)130225.rar

    Hibernate作为ORM框架,负责将Java对象映射到Oracle数据库中的表,使得开发者可以用面向对象的方式来操作数据库,而不需要编写复杂的SQL语句。Spring作为IoC容器,负责管理对象的生命周期和依赖关系,使得系统的各个...

    项目申报系统(Struts2+Spring+Hibernate+Jsp+Mysql5).zip

    通过Hibernate,系统能够提供强大的数据操作能力,简化复杂的数据库交互。 用户管理和权限控制:基于Spring的安全框架,系统支持详细的用户权限管理,确保只有授权用户才能访问敏感信息和功能。 项目监控与报告:...

    本科毕业设计开题报告(计算机协会信息管理系统的设计与实现V5)

    本系统运用Web页面进行前台信息展示,后台偏重于信息管理,两者相互结合,可以使学生在网上进行入社、退社,查询相关社团信息等操作;可以让社团负责人管理自己的社员,在线进行社团活动管理等;可以在线实现社团的...

    JAVA物业管理系统设计与实现.rar

    设计和实现一个基于Java的物业管理系统可以涉及以下方面: 系统模块: 用户管理模块:包括管理...通过以上设计和实现,物业管理系统可以有效地管理物业信息、提高工作效率,同时为业主提供便捷的服务和信息查询功能。

    高校毕业设计管理系统

    B/S结构利用不断成熟和普及的浏览器技术实现原来需要复杂专用软件才能实现的强大功能,并节约了开发成本,是一种全新的软件系统构造技术。  采用B/S结构后,可以把已往发给学生的选题表由浏览器生成,学生直接在...

    java/jdbc简单的ebank电子银行系统

    业务层:实体和负责处理复杂的业务逻辑(EJB, Spring, Javabean) 持久层:负责数据的读取(jdbc,hibernate) 横向分层(业务层与持久层按抽象程度分): 抽象层 实现层 表现层不需要再进行横向分层

    ssh(structs,spring,hibernate)框架中的上传下载

    其中Hibernate 2相关的封装类位于org.springframework.orm.hibernate2.*包中,而Hibernate 3.0的封装类位于org.springframework.orm.hibernate3.*包中,需要根据您所选用Hibernate版本进行正确选择。  3、Lob字段...

    基于J2EE框架的个人博客系统项目毕业设计论文(源码和论文)

    因此,在具体设计实现该博客网站时,主要考虑了主流博客网站的几个主要功能:(1)博客的注册、登录验证功能(2) 网络用户通过关键字搜索博文功能(3) 最热门博客页面推荐浏览(4) 文章详细内容及相关评论显示(5) 博客...

    在线招标系统课程设计.rar

    在线招标系统采用spring,spring mvc框架进行开发,数据库方面由于业务不是太复杂,所以使用了hibernate框架。 该毕业设计主要是将招标投标信息公示出来,系统功能包括:招标公示,投标公示,招标发布,服务商管理等...

    rock-0.9.1开源框架

    4 不支持HQL之类的查询语言,对于复杂查询任务,直接使用sql语言,操作简单,可直接返回对象数据。 5 对于复杂查询任务,sql语句也可以直接放在spring的配置文件中,直接注入到DAO中。 6 不支持对象之间的关联。 7 ...

    java-ee电子商城系统课程设计.doc

    采用SSH2与前台Ajax技术相结合 来实现,在设计过程中全方位的应用软件工程的开发思想,对项目进行UML建模包括各模 块的类图、时序图等。系统基于B/S分布式结构,适应围广阔。 S2SH集成框架是Struts2、Spring 和...

    javaEE-SSH-oracle土地档案管理系统(源码+数据库sql+lun文+视频齐全).rar

    土地档案系统作为将传统的纸质化档案管理方式进行数字化电子化的一项工程,将人类历史上的传承千年的档案管理工作进行数字化的封装,将土地档案管理工作进行了优化,在档案的查询、修改、删除等方面带来了极大的便利...

    基于J2EE的B2C电子商务系统开发

    基于J2EE的B2C电子商务系统开发是一个较为复杂的项目,需要整合多种技术和组件,如Java语言、JSP/Servlet、Struts、Hibernate、Spring等框架、数据库、Web服务器等。以下是一些可能需要考虑的关键技术和步骤: 系统...

    基于SpringJDBC的轻量级ORM框架sborm.zip

    3、实现一套简单的ORM(直接使用spring rowmapper,insert自己实现),可以基于对象进行crud和相对复杂(感觉比hibernate强大一点)的sql操作; 4、基于对象指定查询的字段,大部分时候可以忘掉表结构进行业务...

Global site tag (gtag.js) - Google Analytics