整理SQL查询结果

时间:2017-09-19 18:35:42

标签: sql db2 collate

我不得不为AS400报告编写查询。我们希望按日期对数据进行分组。换句话说,我们想要汇总每个年份和月份的所有数据。这是我目前的查询:

Select SCDATA.SCCLNT.CCLNT,
  (Select SCDATA.SCCLNT.CNAME From SCDATA.SCCLNT
  Where SCDATA.SCCLNT.CLTGRP Like 916500 Fetch First 1 Rows Only) As ClientName,
  CONCAT(TRIM(SCDATA.SCCLNT.CADD1), SCDATA.SCCLNT.CADD2) As Address1,
  CONCAT(TRIM(SCDATA.SCCLNT.CCITY), CONCAT(', ',
  CONCAT(TRIM(SCDATA.SCCLNT.CSTATE), CONCAT('  ', TRIM(SCDATA.SCCLNT.CZIP)))))
  As Address2,
  SCDATA.SCCLNT.CLTGRP As Group,
  SCDATA.SCPLHS.HMONTH || '-' || SCDATA.SCPLHS.HYEAR AS EndDate,

sum(HPL#) as Placed#,
sum (hpl$) as Placed$,
sum(HPMT$M) as PymtMth,
sum(HPMT$) as PymtTTL,
sum(HCOM$) as CommTTL,
sum(HPIF#) as PIF,
sum(HCLI#) as WithDrawn#,
sum(HCLI$) as WithDrawn$,
sum(HCLA#) as Closed#,
sum(HCLA$) as Closed$,
sum(HPMT$)/sum(HPL$) as Recovered,
sum(HAC#) as Active#,
sum(HAC$) as Active$


From SCDATA.SCCLNT
  Inner Join SCDATA.SCPLHS On SCDATA.SCPLHS.HCLNT = SCDATA.SCCLNT.CCLNT And
    (SCDATA.SCPLHS.HYEAR Between 17 And 17) and
(SCDATA.SCPLHS.HMONTH Between 01 And 10 )

Where SCDATA.SCCLNT.CLTGRP Like 916500
Group By     SCDATA.SCPLHS.HYEAR ,
             SCDATA.SCPLHS.HMONTH,
SCDATA.SCCLNT.CCLNT,
SCDATA.SCCLNT.CADD1,
SCDATA.SCCLNT.CADD2,
SCDATA.SCCLNT.CZIP,
SCDATA.SCCLNT.CLTGRP,
SCDATA.SCCLNT.CCITY,
SCDATA.SCCLNT.CSTATE

如何整理这个日期,以便我的结果只显示每个日期一次,以及该日期所有数据的总和?

比你。

- EDIT--
以下是我从当前查询得到的结果,制表符分隔:
https://drive.google.com/open?id=0BwJ_JKr6NhYJVnNIVDcyNW9WMms CSV文件

我需要的结果是:
https://drive.google.com/open?id=0BwJ_JKr6NhYJUTBDUTlDV00yanc

2 个答案:

答案 0 :(得分:0)

当我对查询结果进行分组时,我在组中包含了SCCLNT列。每个客户端组都有多个客户端编号,这导致查询返回多个结果,每个客户端ID一个。

答案 1 :(得分:0)

您的语句存在聚合问题 - 您的GROUP BY包含两个单独的表,其中的列不会共享索引(很可能其中一个表可能没有索引使用的列所有)。该陈述将比它需要的要慢。

您可能会发现仅根据实际销售数据进行汇总的速度更快:

SELECT Client.group, Client.name, Client.address1, Client.address2,
       Historical.month || '-' || Historical.year as endDate
       Historical.placed#, Historical.placed$,
       Historical.pymtMth,
       Historical.pymtTTL, Historical.commTTL,
       Historical.PIF,
       Historical.withdrawn#, Historical.withdrawn$,
       Historical.closed#, Historical.closed$,
       Historical.recovered,
       Historical.active#, Historical.active$
FROM (SELECT SCPlHs.hYear as year, 
             SCPlHs.hMonth as month,
             SUM(SCPlHs.hPl#) as placed#,
             SUM(SCPlHs.hPl$) as placed$,
             SUM(SCPlHs.hpmt$m) as pymtMth,
             SUM(SCPlHs.hPmt$) as pymtTTL,
             SUM(SCPlHs.hCom$) as commTTL,
             SUM(SCPlHs.hPif#) as PIF,
             SUM(SCPlHs.hCli#) as withdrawn#,
             SUM(SCPlHs.hCli$) as withdrawn$,
             SUM(SCPlHs.hCla#) as closed#,
             SUM(SCPlHs.hCla$) as closed$,
             SUM(SCPlHs.hPmt$) / SUM(SCPlHs.hpl$) as recovered,
             SUM(SCPlHs.hAc#) as active#,
             SUM(SCPlHs.hAc$) as active$
      FROM SCData.SCPlHs
      JOIN (SELECT DISTINCT cClnt as client
            FROM SCData.SCClnt
            WHERE SCClnt.cltGrp = 916500) Client
      ON Client.client = SCPlHs.hClnt
      -- dates, like all positive, contiguous-range types,
      -- should be queries with an exclusive upper bound.
      -- You should stop using BETWEEN, if possible.
      WHERE SCPlHs.hYear >= 17 and SCPlHs.hYear < 18
            AND SCPlHs.hMonth >= 1 and SCPlHs.hMonth < 11
      GROUP BY SCPlHs.hYear, SCPlHs.hMonth) Historical
-- Cross joins multiply the total number of rows, but that's okay here because
-- the joined table is going to only have one row
CROSS JOIN (SELECT SCClnt.cltGrp as group
                   SCClnt.cName as name,
                   TRIM(SCClnt.cAdd1) || TRIM(SCClnt.cAdd2) as address1,
                   TRIM(SCClnt.cCity) || ', ' || TRIM(SCClnt.cState) || ' ' || TRIM(SCClnt.cZip) as address2
            FROM SCData.SCClnt
            WHERE SCClnt.cltGrp = 916500
            FETCH FIRST 1 ROW ONLY) Client
ORDER BY Historical.year, Historical.month