连接不正常的max()函数 - DB2 SQL

时间:2015-05-14 20:54:45

标签: sql db2-400

我有一个查询,其中我试图找到在某些字段中包含最大值的行。我尝试了max(field_name),但它返回所有行。

SELECT CMNT.ID, MAX(CMNT.SEQ_NBR) AS SEQ, CMNT.VER_NBR AS VERSION 
FROM 
CUSTOMER_CMNT AS CMNT
INNER JOIN CUSTOMER_PROD AS PRODUCT ON PRODUCT.PRODUCT_ID = CMNT.BALE_ID 
LEFT JOIN CUSTOMER_LOAN LOAN ON (PRODUCT.LOAN_ID = LOAN.LOAN_ID) AND (PRODUCT.START_YR = LOAN.START_YR) AND (PRODUCT.ST_CD = LOAN.ST_CD) AND (PRODUCT.CNTY_CD = LOAN.CNTY_CD)
WHERE CMNT.ID > 0 AND PRODUCT.START_YR = 2013 AND LOAN.LOAN_NBR = 17124
GROUP BY CMNT.VER_NBR, CMNT.SEQ_NBR, CMNT.ID, CMNT.CMNT_TXT

输出

+----------------+------+---------+
| CMNT.ID        | SEQ  | VERSION |
+----------------+------+---------+
 133340000101373   2       1
 133340000101374   2       1
 133340000101373   3       1
 133340000101374   3       1
 133340000101373   4       1
 133340000101374   4       1
 133340000101373   1       2
 133340000101374   1       2
 133340000101373   1       3
 133340000101374   1       3
 133340000101373   2       3
 133340000101374   2       3

但是,预期的行是(max(SEQ_NBR)):

+----------------+------+---------+
| CMNT.ID        | SEQ  | VERSION |
+----------------+------+---------+
 133340000101373   4       1
 133340000101374   4       1

但是我修改了下面的查询,返回上面的预期结果。

SELECT CMNT.ID, MAX(CMNT.SEQ_NBR) AS SEQ, CMNT.VER_NBR AS VERSION 
FROM 
CUSTOMER_CMNT AS CMNT
INNER JOIN CUSTOMER_PROD AS PRODUCT ON PRODUCT.PRODUCT_ID = CMNT.BALE_ID 
LEFT JOIN CUSTOMER_LOAN LOAN ON (PRODUCT.LOAN_ID = LOAN.LOAN_ID) AND (PRODUCT.START_YR = LOAN.START_YR) AND (PRODUCT.ST_CD = LOAN.ST_CD) AND (PRODUCT.CNTY_CD = LOAN.CNTY_CD)
WHERE CMNT.ID > 0 AND PRODUCT.START_YR = 2013 AND LOAN.LOAN_NBR = 17124
CMNT.SEQ_NBR = (select max(CMNT.SEQ_NBR) from   
FROM 
CUSTOMER_CMNT AS CMNT
INNER JOIN CUSTOMER_PROD AS PRODUCT ON PRODUCT.PRODUCT_ID = CMNT.BALE_ID 
LEFT JOIN CUSTOMER_LOAN LOAN ON (PRODUCT.LOAN_ID = LOAN.LOAN_ID) AND (PRODUCT.START_YR = LOAN.START_YR) AND (PRODUCT.ST_CD = LOAN.ST_CD) AND (PRODUCT.CNTY_CD = LOAN.CNTY_CD)
WHERE CMNT.ID > 0 AND PRODUCT.START_YR = 2013 AND LOAN.LOAN_NBR = 17124)

由于子查询,此查询变得更长。有没有办法缩短/改进这个查询?

2 个答案:

答案 0 :(得分:0)

这个怎么样?不确定它是否表现更好......

declare @data table (cmnt_id bigint, seq int, version int)

insert into @data
values (133340000101373, 2, 1), (133340000101374, 2, 1), (133340000101373, 3, 1), (133340000101374, 3, 1), (133340000101373, 4, 1), (133340000101374, 4, 1), (133340000101373, 1, 2), (133340000101374, 1, 2), (133340000101373, 1, 3), (133340000101374, 1, 3), (133340000101373, 2, 3), (133340000101374, 2, 3)

select d.cmnt_id, d.seq, d.version
from @data d
inner join (
    select cmnt_id, max(seq) as target_seq
    from @data
    group by cmnt_id
    ) x on x.cmnt_id = d.cmnt_id
    and d.seq = x.target_seq
order by d.cmnt_id

答案 1 :(得分:0)

理想情况下,您通过Visual Explain工具冷却运行查询,并建议它认为缺少的索引。

除此之外,我肯定会推荐以下索引/密钥:

CUSTOMER_CMNT
   index1 => BALE_ID
   index2 => ID, SEQ_NBR

CUSTOMER_PROD
   index1 => START_YR
   index2 => LOAN_ID, START_YR, ST_CD, CNTY_CD

CUSTOMER_LOAN
   index1 => LOAN_NBR
   index2 => LOAN_ID, START_YR, ST_CD, CNTY_CD

HTH!