从嵌套子查询中选择不同的计数

时间:2014-02-05 18:58:10

标签: sql db2

我正在尝试使用具有左连接的查询进行分页。这导致我的计数是行数,而不是产品数量。用来解释我的问题

SELECT * FROM (
SELECT 
  DENSE_RANK() OVER (order by tmp.prodId, tmp.prodYear) as rnum, 
  COUNT(*) OVER () AS totalRecords,
  tmp.* 
FROM (
  SELECT
    product.*, widget.* 
  FROM A_PROD product
  LEFT JOIN A_WID widget
    ON product.prodId = widget.prodId
    AND product.prodYear = widget.prodYear
  ORDER BY product.prodId ASC ) tmp
)
WHERE rnum BETWEEN 1 and 10

这导致

|rnum|totalRecords|prodId|prodYear|widgetId|
| 1  |     3      | 13   |  2013  |  xyz   |
| 1  |     3      | 13   |  2013  |  abc   |
| 1  |     3      | 13   |  2013  |  mno   |

当我正在寻找的是

|rnum|totalRecords|prodId|prodYear|widgetId|
| 1  |     1      | 13   |  2013  |  xyz   |
| 1  |     1      | 13   |  2013  |  abc   |
| 1  |     1      | 13   |  2013  |  mno   |

这样orm会将它们视为具有不同小部件的相同产品,分页会将其视为输出中的一行,并且“显示X产品中的Y”消息将是正确的。

这可行吗?

2 个答案:

答案 0 :(得分:2)

如果我理解正确,你想要计算输出中的prodid(或者是prodid / year对)。如果是,请将逻辑移至外部查询,以便where影响它。这可能有效:

SELECT count(distinct prodid) over () as totalRecords, t.*
FROM (SELECT DENSE_RANK() OVER (order by tmp.prodId, tmp.prodYear) as rnum, 
             tmp.* 
      FROM (SELECT product.*, widget.* 
            FROM A_PROD product LEFT JOIN
                 A_WID widget
                 ON product.prodId = widget.prodId AND product.prodYear = widget.prodYear
          ) tmp
    ) t
WHERE rnum BETWEEN 1 and 10
order by prodId ASC;

注意:我不认为子查询中的order by有效。我把它移到外部查询。

而且,我不知道DB2是否支持count(distinct)作为窗口/分析函数。如果没有,则有一种解决方法。

编辑:

如果count中没有明显,则可以将行号返回1的值相加:

SELECT sum(case when rnum = 1 then 1 else 0 end) over () as totalprodyear, t.*
FROM (SELECT DENSE_RANK() OVER (order by tmp.prodId, tmp.prodYear) as rnum, 
             tmp.* 
      FROM (SELECT product.*, widget.* 
            FROM A_PROD product LEFT JOIN
                 A_WID widget
                 ON product.prodId = widget.prodId AND product.prodYear = widget.prodYear
          ) tmp
    ) t
WHERE rnum BETWEEN 1 and 10
order by prodId ASC;

重要prodyear。如果您只需要prod,请仅在row_number()上添加其他prodid分区。

答案 1 :(得分:0)

我无法得到戈登·林诺夫的工作答案,但确实给了我一个想法。

SELECT * FROM (
SELECT MAX(rnum) OVER () as totalprodyear, t.*
FROM (SELECT DENSE_RANK() OVER (order by tmp.prodId, tmp.prodYear) as rnum, 
             tmp.* 
      FROM (SELECT product.*, widget.* 
            FROM A_PROD product LEFT JOIN
                 A_WID widget
                 ON product.prodId = widget.prodId AND product.prodYear = widget.prodYear
          ) tmp
    ) t
)
WHERE rnum BETWEEN 1 and 10
order by prodId ASC;

为我的目的而努力