0

我有一个基于标准的查询,具有以下分组:

Projections.projectionList()
    .add(Property.forName("xyz").group()));

生成的 SQL 是(专有的,因此已清理):

select this_.XYZ as y0_ from FOO.BAR this_ WHERE [long where clause] 
    group by this_.XYZ

现在,从概念上讲,我想用 count(*) 包装查询结果,这样数据就永远不会从数据库中返回,而只是计数。像这样:

select count(*) from (
  select this_.XYZ as y0_ from FOO.BAR this_ WHERE [long where clause] 
      group by this_.XYZ
)

可能有数千行我不需要并且我对高性能感兴趣,所以我不希望这些数据通过网络传输。

我的基于条件的搜索有许多条件。我无法真正重建它,所以我真的需要坚持使用 Criteria。

当然,添加 rowCount 或 count("xyz") 没有帮助,因为它只为每一行报告 1。

我目前正在这样做以获取计数:

ScrollableResults scroll = criteria.scroll();
scroll.last();
int count = scroll.getRowNumber();

它有效,但需要很长时间才能返回计数(如果重要,请在 Oracle 上)。

我可以按照我的提议去做吗?

4

2 回答 2

7

从概念上讲,

select count(*) from (
  select this_.XYZ as y0_ from FOO.BAR this_ WHERE [long where clause] 
      group by this_.XYZ
)

是相同的

select count(distinct (this_.XYZ)) from FOO.BAR this_ WHERE [long where clause] 

因此,您可以使用Projections.countDistinct((String propertyName))为您的 Criteria 选择不同的 propertyName。

session.createCriteria(Foo.class)
        .add(myOrigianlCriterionObject)
        .setProjection(Projections.countDistinct("XYZ"));
于 2011-09-14T06:33:26.957 回答
0

使用Subqueries API和创建内部标准。

第一个标准是分组依据包含在其中的主要标准。行数取自第二个标准 100% 保证结果。

第一个标准

DetachedCriteria criteria = getNominationMainCriteria(nominationFilterDto, appraiserId);
        criteria.add(Property.forName(PROFFESIONAL_STRING + ".hcpId").eqProperty("subProf.hcpId"));
        criteria.setProjection(Projections.projectionList().add(
                Projections.groupProperty(PROFFESIONAL_STRING + "." + Constants.HCP_ID)));

第二个标准

Criteria nativeCriteria = getSession().createCriteria(Professional.class, Constants.SUB_PROFESSIONAL);
        nativeCriteria.add(Subqueries.propertyEq(Constants.SUB_PROFESSIONAL + "." + Constants.HCP_ID, criteria));
        nativeCriteria.setProjection(Projections.projectionList().add(Projections.rowCount()));
        rowCount = (Long) nativeCriteria.uniqueResult();
于 2013-09-09T08:03:05.920 回答