爪哇一角

          共同探討STRUTS#HIBERNATE#SPRING#EJB等技術(shù)
          posts - 3, comments - 6, trackbacks - 0, articles - 99
            BlogJava :: 首頁(yè) :: 新隨筆 :: 聯(lián)系 :: 聚合  :: 管理

          Hibernate綜合查詢解決方案

          這兩個(gè)星期以來(lái),我把原來(lái)用struts開發(fā)的一個(gè)測(cè)試工具改用struts+hibernate來(lái)實(shí)現(xiàn),首先從心情上來(lái),整個(gè)開發(fā)過(guò)程中始終保持愉快和平和,“原來(lái)開發(fā)可以這樣愉快?”,再一點(diǎn)就是開發(fā)效率上高效了許多。
          ????? 現(xiàn)在sun又加入jdocentral.com開始著手JDO2.0,想想看等它出臺(tái)以后將是一個(gè)怎樣激動(dòng)人心得場(chǎng)面,讓我們拭目以待。
          ?????
          ????? 用Hibernate來(lái)操縱持久數(shù)據(jù)非常簡(jiǎn)單,在這里一些簡(jiǎn)單的查詢我會(huì)一筆帶過(guò),本文著重說(shuō)明在綜合查詢兼有分頁(yè)的時(shí)候我的一些經(jīng)驗(yàn),如果網(wǎng)友覺得我的方案還有不足的地方,也請(qǐng)和我討論,我的email:plateau_t@sina.com.
          ?????
          ????? 第一部分:Hibernate提供的查詢接口或其方法(此部分不做深究,請(qǐng)參考hibernate手冊(cè))
          ?????
          ?????? 1。根據(jù)ID查詢
          ?? ?要用到Session接口的load方法。
          ?? ?load(Class theClass, Serializable id)
          ?? ?load(Class theClass, Serializable id, LockMode lockMode)
          ?? ?load(Object object, Serializable id)?
          ?? ?
          ?????? 2。HQL語(yǔ)句進(jìn)行查詢
          ??????
          ?????? 2。1 利用Query接口,Query由Session里的createQuery()來(lái)產(chǎn)生一個(gè)查詢
          ?? ???? 1)不帶參數(shù)的查詢(這類比較簡(jiǎn)單)
          ?? ???? Query query=session.createQuery("select user from User as user");
          ?? ???? 2)帶參數(shù)的查詢
          ?? ???? Query query=session.createQuery("select user from User as user where user.name=?");
          ?? ???? query.setString(0,name)//假設(shè)name為傳過(guò)來(lái)的參數(shù)
          ?? ???? Query query=session.createQuery("select user from User as user where user.name=:name");
          ?? ???? query.setString("name",name)//假設(shè)name為傳過(guò)來(lái)的參數(shù)
          ?? ???? (多個(gè)參數(shù)以此類推)
          ?? ????
          ?? ???? 利用Session接口的find查詢
          ?? ???? find(String query)
          ?? ???? find(String query, Object[] values, Type[] types)
          ?? ???? find(String query, Object value, Type type)? ? 均返回list??
          ?? ???? 如:
          ?? ???? List list=session.find("select user from Users as user where user.name=?",name,Hibernate.STRING)
          ?? ???? List list=session.find("select user from Users as user where user.name=? and???????????? user.pw=?",new Object[]{name,pw},new Type[]{Hibernate.STRING,Hibernate.STRING})
          ?? ????
          ?? ???? {推薦使用Query的方法進(jìn)行查詢}??
          ?? ????
          ????? 第二部分:hibernate綜合查詢解決方案 (此部分詳細(xì)實(shí)例說(shuō)明,如有不足的地方請(qǐng)寫信給我)????????
          ?????
          ????? ?大家從第一部分可以看到,帶有參數(shù)的查詢,必須使用到Query接口,如上邊:
          ?? ???? Query query=session.createQuery("select users from Users as users where users.name=?");
          ?? ???? query.setString(0,name)//假設(shè)name為傳過(guò)來(lái)的參數(shù)???
          ???? ??但是在系統(tǒng)中如何才能寫一個(gè)公用的查尋方法呢?咋一看,似乎是不可以的,因?yàn)槊恳淮尾樵兊膮?shù)不一樣,參數(shù)的數(shù)量不一樣(如下代碼),那么我們?nèi)绾翁崛」残阅兀? ?
          ??? ???? Query query=session.createQuery("select users from Users as users where users.name=? and users.pw=?");
          ?? ???? query.setString(0,name)//假設(shè)name為傳過(guò)來(lái)的參數(shù)?
          ?? ???? query.setString(1,pw);
          ?? ???
          ?? ?? 首先說(shuō)明,我的解決方案是從Seesion接口的find方法找到出口的,如下為Session接口得find()方法之一:
          ?? ???? find(String query, Object[] values, Type[] types)?
          ?? ?? 其中Object[]為存放參數(shù)值的數(shù)組,Type[]為存放參數(shù)類型的數(shù)組,他們的順序是和query里“?” 的順序是相同的。那么我為什么不用該find方法呢,因?yàn)槿绻蟹猪?yè)的情況,那么該方法將不適用。
          ?? ?
          ?? ?? 下面詳細(xì)要說(shuō)明的解決方案:
          ?? ?? 首先我想創(chuàng)建三個(gè)新的對(duì)象:Paras.java(參數(shù)對(duì)象) ParasList.java(參數(shù)集合對(duì)象)HQuery.java
          ?? ? (感謝我的同事camel提供注釋良好的代碼)
          ??? ?1。Paras.java(參數(shù)對(duì)象)
          ?? ?
          ??package com.ifreeway.homegrown.testing.waf;
          ??
          ??/**
          ?? *
          ?? * <p>Title:定義一個(gè)sql語(yǔ)句的條件參數(shù)類 </p>
          ?? * <p>Description: 可以使用有序的參數(shù)集合傳送給sql/hql語(yǔ)句 </p>
          ?? * <p>Copyright: Copyright (c) 2003</p>
          ?? * <p>Company: ifreeway</p>
          ?? * @author camel
          ?? * @version 1.0
          ?? */
          ??
          ??public class Paras {
          ???/**
          ??? * 參數(shù)名稱
          ??? */
          ???private Object pName;
          ???/**
          ??? * 參數(shù)類型編碼,于java.sql.types中的類型保持一致
          ??? */
          ???private int typeNo;
          ??
          ???public Object getPName() {
          ????return pName;
          ???}
          ???public void setPName(Object pName) {
          ????this.pName = pName;
          ???}
          ???public int getTypeNo() {
          ????return typeNo;
          ???}
          ???public void setTypeNo(int typeNo) {
          ????this.typeNo = typeNo;
          ???}
          ??}?
          ?
          ?2。ParasList.java(參數(shù)集合對(duì)象)?
          ??package com.ifreeway.homegrown.testing.waf;
          ??
          ??import java.util.ArrayList;
          ??
          ??/**
          ?? *
          ?? * <p>Title: 參數(shù)集合類</p>
          ?? * <p>Description: 封裝sql/hql的參數(shù)到該集合類,便于處理和傳遞</p>
          ?? * <p>Copyright: Copyright (c) 2003</p>
          ?? * <p>Company: ifreeway</p>
          ?? * @author camel
          ?? * @version 1.0
          ?? */
          ??
          ??public class ParaList extends ArrayList {
          ??
          ??? /**
          ???? * 在指定位置添加一個(gè)參數(shù)對(duì)象
          ???? * @param index:參數(shù)的索引值
          ???? * @param p:需要加入的參數(shù)對(duì)象
          ???? */
          ??? public? void addParas(int index,Paras p){
          ??????? super.add(index,p);
          ??? }
          ??
          ??? /**
          ???? * 在集合的最后位置添加一個(gè)參數(shù)對(duì)象
          ???? * @param p:需要加入的參數(shù)對(duì)象
          ???? */
          ??? public void addParas(Paras p){
          ????? super.add(p);
          ??? }
          ??
          ??? /**
          ???? * 取得指定位置的參數(shù)對(duì)象
          ???? * @param index:參數(shù)的索引值
          ???? * @return:參數(shù)對(duì)象
          ???? */
          ??? public Paras getParas(int index){
          ??????? return (Paras)super.get(index) ;
          ??? }
          ??? /**
          ???? * 取得指定參數(shù)的索引
          ???? * @param p:參數(shù)對(duì)象
          ???? * @return:參數(shù)索引
          ???? */
          ??? public int indexofParas(Paras p){
          ?????? return super.indexOf(p) ;
          ??? }
          ??
          ??? /**
          ???? * 從集合中去掉一個(gè)指定的參數(shù)對(duì)象
          ???? * @param index:參數(shù)索引
          ???? */
          ??? public void removeParas(int index){
          ????? super.remove(index) ;
          ??? }?
          ??
          ??}?
          ?3。HQuery.java
          ??package com.ifreeway.homegrown.testing.waf;
          ??
          ??
          ??/**
          ?? *
          ?? * <p>Title: HQL的語(yǔ)句封裝類</p>
          ?? * <p>Description: 該對(duì)象封裝HQL的查詢語(yǔ)句,參數(shù)集合,排序參數(shù),分組參數(shù),單頁(yè)起始地址? </p>
          ?? * <p>Copyright: Copyright (c) 2003</p>
          ?? * <p>Company:ifreeway </p>
          ?? * @author camel
          ?? * @version 1.0
          ?? */
          ??
          ??public class HQuery {
          ??
          ??? /**
          ???? * HQL查詢語(yǔ)句
          ???? */
          ??? private String queryString;
          ??? /**
          ???? * 參數(shù)集合對(duì)象
          ???? */
          ??? private ParaList paralist;
          ??? /**
          ???? * 排序字段
          ???? */
          ??? private String orderby;
          ??? /**
          ???? * 分組字段
          ???? */
          ??? private String groupby;
          ??? /**
          ???? * 分頁(yè)起始查詢地址
          ???? */
          ??? private int pageStartNo;
          ??
          ??? /**
          ???? * 取得一個(gè)Hibernate的Query對(duì)象
          ???? * @return:Query對(duì)象
          ???? */
          ??? public String getQueryString() {
          ????? return queryString;
          ??? }
          ??
          ??? /**
          ???? * 設(shè)置一個(gè)HQL查詢字符串
          ???? * @param queryString:查詢字符串
          ???? *
          ???? */
          ??? public void setQueryString(String queryString) {
          ??
          ???? this.queryString =queryString;
          ??
          ??? }
          ??
          ??? /**
          ???? * 取得參數(shù)集合對(duì)象
          ???? * @return:參數(shù)集合對(duì)象
          ???? */
          ??? public ParaList getParalist() {
          ????? return paralist;
          ??? }
          ??
          ??? /**
          ???? * 設(shè)置參數(shù)集合對(duì)象
          ???? * @param paralist:參數(shù)集合對(duì)象
          ???? */
          ??? public void setParalist(ParaList paralist) {
          ????? this.paralist = paralist;
          ??? }
          ??
          ??? /**
          ???? * 取得排序字段
          ???? * @return:排序字段
          ???? */
          ??? public String getOrderby() {
          ????? return orderby;
          ??? }
          ??
          ??? /**
          ???? * 設(shè)置排序字段
          ???? * @param orderby
          ???? */
          ??? public void setOrderby(String orderby) {
          ????? this.orderby = orderby;
          ??? }
          ??
          ??? /**
          ???? * 取得分組字段
          ???? * @return
          ???? */
          ??? public String getGroupby() {
          ????? return groupby;
          ??? }
          ??
          ??? /**
          ???? * 設(shè)置分組字段
          ???? * @param groupby
          ???? */
          ??? public void setGroupby(String groupby) {
          ????? this.groupby = groupby;
          ??? }
          ??
          ??? /**
          ???? * 取得頁(yè)起始地址
          ???? * @return
          ???? */
          ??? public int getPageStartNo() {
          ????? return pageStartNo;
          ??? }
          ??
          ??? /**
          ???? * 設(shè)置頁(yè)起始地址
          ???? * @param pageStartNo
          ???? */
          ??? public void setPageStartNo(int pageStartNo) {
          ????? this.pageStartNo = pageStartNo;
          ??? }
          ??}?
          ??
          ?上面三個(gè)對(duì)象的關(guān)系是:
          ?
          ?用Paras來(lái)裝載每一個(gè)查詢參數(shù)
          ??Paras paras=new Paras();
          ??paras.setPName(...);
          ??paras.setTypeNo(...);
          ?然后放在ParasList中
          ??ParasList paraslist=new ParasList();
          ??paraslist.add(paras)
          ?最后把填充以后的ParasList集合給HQuery?
          ??HQuery hquery=new HQuery();
          ??hquery.setParalist(paraslist);
          ??
          ?先面我們寫一個(gè)公用查尋方法,來(lái)實(shí)現(xiàn)我們的綜合查詢:
          ?
          ?/**
          ? *
          ? *? 綜合查詢,首先實(shí)例化HQuery
          ? * @see com.ifreeway.homegrown.testing.common.waf.DBHandler#find(com.ifreeway.homegrown.testing.common.waf.HQuery)
          ? */
          ?public List find(HQuery _query) throws HibernateException {
          ??List itr = null;
          ??try {
          ???StringBuffer query_str = new StringBuffer(_query.getQueryString());
          ???//是否要排序
          ???if (_query.getOrderby() != null) {
          ????query_str.append(_query.getOrderby());
          ???}
          ???//是否要分組
          ???if (_query.getGroupby() != null) {
          ????query_str.append(_query.getGroupby());
          ???}
          ???Session session = getSession();
          ???Query query = session.createQuery(query_str.toString());
          ???if (_query.getParalist() != null) {
          ????List list = _query.getParalist();
          ????for (int i = 0; i < list.size(); i++) {
          ?????Paras param = (Paras) list.get(i);
          ?????switch (param.getTypeNo()) {//此處要根據(jù)參數(shù)類型的增加要增加相應(yīng)的“case”
          ??????case Types.VARCHAR :
          ???????query.setString(i, param.getPName().toString());
          ???????break;
          ??????case Types.INTEGER :
          ???????query.setInteger(
          ????????i,
          ????????((Integer) param.getPName()).intValue());
          ???????break;
          ??????case Types.DATE :
          ???????query.setDate(i, (java.sql.Date) param.getPName());
          ???????break;
          ??????case Types.DOUBLE :
          ???????query.setDouble(
          ????????i,
          ????????((Double) param.getPName()).doubleValue());
          ???????break;
          ??????case Types.BOOLEAN :
          ???????query.setBoolean(
          ????????i,
          ????????((Boolean) param.getPName()).booleanValue());
          ???????break;
          ??????case Types.CHAR :
          ???????query.setCharacter(
          ????????i,
          ????????((Character) param.getPName()).charValue());
          ???????break;
          ??????case Types.JAVA_OBJECT :
          ???????query.setEntity(i, (BaseModel) param.getPName());
          ???????break;
          ?????}
          ????}
          ???}
          ???//是否存在分頁(yè),當(dāng)_query.getPageStartNo()==0是不分頁(yè)
          ???if (_query.getPageStartNo() != 0) {
          ????int pageno = _query.getPageStartNo();
          ????query.setFirstResult((pageno - 1) * Constants.RECORD_PER_PAGE);
          ????query.setMaxResults((pageno) * Constants.RECORD_PER_PAGE);
          ???}
          ???itr = query.list();
          ?? closeSession();
          ??} catch (Exception e) {

          ??}
          ??return itr;
          ?}?
          ?? ?
          ????? 好了一旦我們做好了上邊的工作,查詢對(duì)我們來(lái)說(shuō)將是很容易的一件事情,而且可以達(dá)到公用,是不是省了許多力氣?下面我將實(shí)例化一個(gè)例子來(lái)進(jìn)一步說(shuō)明:
          ?????
          ????? 例子:
          ????? HQuery hquery=HQuery();
          ????? hquery.setQueryString("select users from Users as users where users.name=? and users.sex=?");
          ????? hquery.setOrderby("order by users.age desc");
          ?????
          ????? //如果要分頁(yè),把當(dāng)前頁(yè)curpage傳遞給hquery
          ????? hquery.setPageStartNo(curpage);
          ?????
          ????? //實(shí)例化參數(shù),本例為兩個(gè)參數(shù)
          ????? Paras paras1=new Paras();
          ????? paras1.setPName(name);
          ????? paras1.setTypeNo(Types.VARCHAR);
          ?????
          ????? Paras paras2=new Paras();
          ????? paras2.setPName(sex);
          ????? paras2.setTypeNo(Types.INTEGER);
          ?????
          ????? ParasList paraslist=new ParasList();
          ????? paraslist.add(paras1);
          ????? paraslist.add(paras2);//注意順序
          ?????
          ????? hquery.setParalist(paraslist);
          ?????
          ????? //好了,做好準(zhǔn)備工作,調(diào)用查尋方法得到結(jié)果
          ????? List list=find(hquery);
          ??????
          ?????

          主站蜘蛛池模板: 揭东县| 鹤峰县| 循化| 辛集市| 伊春市| 长春市| 高州市| 布尔津县| 湘乡市| 岫岩| 马鞍山市| 兴安县| 阆中市| 紫阳县| 黄冈市| 汉阴县| 怀安县| 武汉市| 盐亭县| 鹤壁市| 新干县| 和林格尔县| 浙江省| 深州市| 噶尔县| 永兴县| 扎鲁特旗| 澎湖县| 乐昌市| 馆陶县| 那坡县| 中超| 青阳县| 织金县| 永丰县| 平舆县| 合作市| 哈巴河县| 法库县| 海林市| 乌兰察布市|