`

hibernate ResultTransformer (转)

 
阅读更多

Using ResultTransformer

gengmzh

2010-7-5

 

ResultTransformer Hibernate 的查询结果转换器,在 HQL SQL Criteria 等查询方式中都支持,可以将查询结果灵活地转换为需要的对象,如 Map non-entity bean

 

ResultTransformer 列表

Hibernate 本身提供了下列 transformer

 
 

ResultTransformer 接口

transformTuple :处理单行查询结果,将其转换为最终对象。 Hibernate 在处理单行查询结果时,最后调用该方法。

transformList :统一处理最终查询结果集,将其转化为最终对象。 Hibernate 在处理查询结果集时,最后会调用该方法。

 

AliasToBeanConstructorResultTransformer

transformTuple :以单行查询结果为参数,通过构造子实例化最终对象。

transformList :不做处理。

 

AliasToBeanResultTransformer

transformTuple :以查询时指定的属性别名作为最终对象的属性名,通过反射实例化最终对象,并调用属性的 setter 方法将查询结果值设置到最终对象里。

transformList :不做处理。

 

BasicTransformerAdapter

ResultTransformer 的空操作实现类,且是抽象的。

 

AliasToEntityMapResultTransformer

transformTuple :以查询时指定的别名作为 key ,以结果值作为 value ,将单行查询结果组装成一个 Map

transformList :不做处理。

 

DistinctResultTransformer

transformTuple :不做处理。

transformList :剔除重复的对象,按照 == 判断查询结果是否相同。

 

PassThroughResultTransformer

transformTuple 如果单行结果只有一个元素则直接返回该元素值,否则不做处理。

transformList :不做处理。

 

RootEntityResultTransformer

transformTuple :返回最后一个元素,也就是根实体对象。

transformList :不做处理。

 

ToListResultTransformer

transformTuple :将单行查询结果由数组转换为 List

transformList :不做处理。

 

DistinctRootEntityResultTransformer

DistinctResultTransformer RootEntityResultTransformer 的组合。

transformTuple :返回最后一个元素,也就是根实体对象。

transformList :剔除重复的对象,按照 == 判断查询结果是否相同。

 

应用示例

AliasToBeanResultTransformer 为例

设若我们有简单的视图层广告物料 Bean ViewAd ,对应复杂的广告物料实体 Ad ViewAd id 对应 Ad adId ,如下:

通过 AliasToBeanResultTransformer 可以直接将查询结果转换为 ViewAd (当然在只需查询 ViewAd 属性的情况下)。

Criteria 查询

public List<ViewAd> queryAd(Integer userId, String keyword) {

         Criterion res = Restrictions.eq("this.userId", userId);

         Criteria crit = adDao.createCriteria(res);

         crit.add(Restrictions.like("this.name", keyword, MatchMode.ANYWHERE));

         ProjectionList pl = Projections.projectionList();

         pl.add(Property.forName("adId"), "id"); // 注:别名需与 ViewAd 中的属性名一致

         pl.add(Property.forName("name"), "name");

         pl.add(Property.forName("width"), "width");

         pl.add(Property.forName("height"), "height");

         pl.add(Property.forName("type"), "type");

         pl.add(Property.forName("status"), "status");

         crit.setProjection(pl).setResultTransformer(new AliasToBeanResultTransformer(ViewAd.class));

         return crit.list();

}

 

HQL 查询

public List<ViewAd> queryAd(Integer userId, String keyword) {

         StringBuffer hql = new StringBuffer();

         hql.append("select ad.adId as id, ");  // 注:需通过 as 指定别名

         hql.append("ad.name as name, ");

         hql.append("ad.width as width, ");

         hql.append("ad.height as height, ");

         hql.append("ad.type as type, ");

         hql.append("ad.status as status ");

         hql.append("from Ad ad ");

         hql.append("where ad.userId=? and ad.name like ? ");

         Query query = adDao.createQuery(hql.toString(), userId, "%" + keyword + "%");

         query.setResultTransformer(new AliasToBeanResultTransformer(ViewAd.class));

         return query.list();

}

 

SQL 查询

public List<ViewAd> queryAd(Integer userId, String keyword) {

StringBuffer sql = new StringBuffer();

         sql.append("select ad_id as id, "); // 注:需通过 as 指定别名

         sql.append("name as name, ");

         sql.append("width as width, ");

         sql.append("height as height, ");

         sql.append("type as type, ");

         sql.append("status as status ");

         sql.append("from ad ");

         sql.append("where user_id=:userId and name like :keyword ");

         Map<String, Object> pars = new HashMap<String, Object>();

         pars.put("userId", userId);

         pars.put("keyword", "%" + keyword + "%");

         SQLQuery query = (SQLQuery) adDao.createSQLQuery(sql.toString(), pars);

         query.addScalar("id", Hibernate.INTEGER); // 注:并将 as 的别名声明为一个查询项,并指定类型

         query.addScalar("name", Hibernate.STRING);

         query.addScalar("width", Hibernate.INTEGER);

         query.addScalar("height", Hibernate.INTEGER);

         query.addScalar("type", Hibernate.INTEGER);

         query.addScalar("status", Hibernate.INTEGER);

         query.setResultTransformer(new AliasToBeanResultTransformer(ViewAd.class));

         return query.list();

}

 

自定义 ResultTransformer KeyValueResultTransformer

在某些情况下,我们需要获取某个对象的 id name ,而且要组成一个 Map

没有 ResultTransformer

public Map<Integer, String> queryAdIdAndName(Integer userId, String keyword) {

         Criterion res = Restrictions.eq("this.userId", userId);

         Criteria crit = adDao.createCriteria(res);

         crit.add(Restrictions.like("this.name", keyword, MatchMode.ANYWHERE));

         ProjectionList pl = Projections.projectionList();

         pl.add(Property.forName("adId"), "id");

         pl.add(Property.forName("name"), "name");

         List<Object[]> ol=crit.setProjection(pl).list();

         Map<Integer,String> map=new HashMap<Integer,String>();

         for(Object[] obj:ol){

                   if(obj[0]!=null){

                            map.put((Integer)obj[0], (String)obj[1]);

                   }

         }

         return map;

}

 

使用自定义 KeyValueResultTransformer

public Map<Integer, String> queryAdIdAndName(Integer userId, String keyword) {

         Criterion res = Restrictions.eq("this.userId", userId);

         Criteria crit = adDao.createCriteria(res);

         crit.add(Restrictions.like("this.name", keyword, MatchMode.ANYWHERE));         

         ProjectionList pl = Projections.projectionList();

         pl.add(Property.forName("adId"), "id");

         pl.add(Property.forName("name"), "name");

crit.setProjection(pl).setResultTransformer(new KeyValueResultTransformer<Integer, String>());

return (Map<Integer, String>) crit.uniqueResult();

}

 

KeyValueResultTransformer的实现

transformTuple:不做处理。
transformList:将查询结果集组装成一个Map,实现代码如下:
public class KeyValueResultTransformer<K, V> extends BasicTransformerAdapter {

    private static final long serialVersionUID = 5603955993685930635L;

    @SuppressWarnings("unchecked")
    public List transformList(List list) {
        Map<K, V> kvs = new HashMap<K, V>();
        for (Object[] obj : (List<Object[]>) list) {
            if (obj.length != 2) {
                throw new IllegalArgumentException("one row must have two tuples");
            }
            if (obj[0] != null) {
                kvs.put((K) obj[0], (V) obj[1]);
            }
        }
        List<Map<K, V>> ml = new ArrayList<Map<K, V>>();
        ml.add(kvs);
        return ml;
    }

}

分享到:
评论
1 楼 anybyb 2012-08-01  
受益匪浅,刚刚正好有这个需求,就搜到这篇文章了。

相关推荐

    Hibernate-基础联表模板

    通过ResultTransformer可以转换查询结果,使其满足特定需求。 综上所述,"Hibernate-基础联表模板"涵盖了Hibernate中关于联表查询的基础知识,包括各种查询方式、关联关系的定义、Fetch策略以及查询结果的处理等,...

    hibernate源码包

    10. **org.hibernate.transform**: 结果集转换相关的类,如ResultTransformer,可以将查询结果转换为自定义格式。 另外,"META-INF"目录通常包含项目元数据,例如Maven的pom.xml(项目对象模型)文件,或者MANIFEST...

    hibernate4.22源码

    9. **查询优化**:`org.hibernate.transform`包提供了结果集转换器,例如`ResultTransformer`,可以将查询结果转换为自定义对象。此外,Hibernate还实现了查询缓存和第二级缓存,以提高性能。 10. **实体状态管理**...

    hibernate-release-5.0.11.Final

    5. 结果集转换:使用Hibernate的Transformer或自定义ResultTransformer,将查询结果转化为所需格式。 四、5.0.11.Final版亮点 - 性能优化:对查询性能进行了调整,提升了处理大数据量的能力。 - 错误修复:修复了...

    hibernate5--4.检索方式及策略

    `Session.createSQLQuery()` 可以创建原生的SQL查询,返回的结果可以映射到POJOs或者使用ResultTransformer转换。 总结,"hibernate5--4.检索方式及策略"涵盖了Hibernate中的各种检索技术,包括HQL、Criteria API、...

    hibernate2.

    《Hibernate2. 入门必读》 Hibernate是一款强大的Java对象关系映射(ORM)框架,它极大地简化了Java应用程序与数据库之间的交互。在本文中,我们将深入探讨Hibernate2.的相关知识点,帮助初学者理解并掌握这个框架...

    hibernate入门教程

    使用ResultTransformer可以实现这个功能。 **9. 第二级缓存与查询缓存** Hibernate提供了一级缓存(Session级别的缓存)和二级缓存(SessionFactory级别的缓存)。二级缓存可以提高性能,但需要正确配置和使用。...

    Hibernate3.4.X 代码快速查询 实体更快 更方便

    - 查询结果可以通过ResultTransformer进行转换。 - 提供了多种转换策略,如FetchAllStrategy、FetchEntityStrategy等。 #### 七、过滤器与优化 1. **过滤器**: - 可以为查询添加过滤条件,以进一步缩小搜索...

    Hibernate SQLQuery执行原生SQL.docx

    在Java的Hibernate框架中,有时候我们需要执行自定义的SQL查询以获取特定的数据,这时就可以使用SQLQuery接口。本文将深入探讨Hibernate如何通过SQLQuery接口执行原生SQL查询,并展示如何处理查询结果。 一、创建...

    关联映射hibernate的criteria的用法

    - `transform(ResultTransformer transformer)`: 转换查询结果。例如,`Transformers.aliasToBean(User.class)`将结果转换为User对象列表。 ```java criteria.setProjection(Projections.projectionList() .add...

    hibernate_search_reference.pdf

    - ResultTransformer:介绍了一种转换查询结果的方法。 - 理解结果:提供了理解查询结果的指南。 综上所述,`hibernate_search_reference.pdf` 为开发者提供了一个全面深入的 Hibernate Search 使用手册,涵盖了...

    Query对象setResultTransFormer()

    Query 对象 set_ResultTransformer() 详解 在 Hibernate 中,Query 对象是用来执行 HQL 或 SQL 查询的重要对象。今天我们来探讨 Query 对象的 setResultTransformer() 方法,该方法可以将查询结果转换为指定的对象 ...

    开发中遇到的问题

    - **Hibernate框架查询优化**:在使用Hibernate进行数据库操作时,为了提高查询效率,可以利用`setResultTransformer`方法进行结果转换,如`hibernatequery.setResultTransformer(ResultTransformer transformer)`。...

    Java面试题

    Hibernate中的Criteria查询可以通过设置ResultTransformer为DISTINCT_ROOT_ENTITY来去除查询结果中的重复实体。`dc.setResultTransformer(Criteria.DISTINCT_ROOT_ENTITY);` 这一行代码的作用是确保返回的实体结果...

    300+道中高级java工程师面试题大全含答案文档下载

    1. **Hibernate离线查询去除重复项**:在Hibernate中,使用Criteria API时,可以设置ResultTransformer为`Criteria.DISTINCT_ROOT_ENTITY`来去除查询结果中的重复实体。 2. **HTTP与SMTP协议及端口**:HTTP是用于...

    java工程师面试题大全

    在Hibernate中,如果需要去除查询结果中的重复项,可以使用`Criteria.DISTINCT_ROOT_ENTITY`作为`ResultTransformer`。这将确保返回的实体集合中没有重复的根实体。例如: ```java Criteria criteria = session....

    让JPA的Query查询接口返回Map对象的方法

    当然,你可以通过自定义ResultTransformer的形式对字段名进行一定的处理,甚至是返回自己需要的POJO。 让JPA的Query查询接口返回Map对象的方法可以使用unwrap()方法和setResultTransformer()方法来实现。这样可以...

    NHibernate调用存储过程

    对于每个需要调用的存储过程,我们需要定义一个HBM(Hibernate Mapping By Example)XML文件,或者使用Fluent NHibernate的映射API。下面我们将通过一个简单的增删改查例子来说明。 1. **增加(Insert)**: 在...

Global site tag (gtag.js) - Google Analytics