在项目上选择distinct并返回关联的其他字段

时间:2015-08-11 13:47:19

标签: sql sql-server database select distinct

我有一张批次和日期表。批次不是唯一的,所以如果我在批号上运行select distinct,这将解决问题。

我目前有:

SELECT batch_number, date_received, expiry_date, prod_code, quantity
FROM scheme.stquem
GROUP BY batch_number

这给出了以下错误:

  

列' scheme.stquem.date_received'在选择列表中无效   因为它不包含在聚合函数或   GROUP BY子句。

如何返回与不同批次编号关联的其他字段?

编辑:理想情况下返回每个字段的最小日期/值。

答案:

SELECT batch_number, min(prod_code), min(date_received), min(expiry_date), min(quantity) 
FROM scheme.stquem 
GROUP BY batch_number

2 个答案:

答案 0 :(得分:2)

如果您的评论如下:

  

如果有重复,那么我想取min(date_received),min(expiry_date),min(数量)

然后只使用MIN函数:

SELECT batch_number, MIN(date_received), MIN(expiry_date), MIN(prod_code), MIN(quantity)
FROM scheme.stquem
GROUP BY batch_number;

这种方法存在问题,给出了以下样本数据:

batch_number    date_received   expiry_date prod_code   quantity
-----------------------------------------------------------------
1               2015-08-01      2015-09-01  p1          5
1               2015-08-02      2015-08-08  p1          3
1               2015-08-02      2015-08-09  p0          1

您将从所有不同的行中获取字段,因此您将从第一行获取date_received,从第二行获取expiry_date,从prod_codequantity获取第三个。这是有效的,聚合是有用的,但我不确定这是你想要的。

相反,我想您可能希望在每个batch_number中对行进行排名,您可以使用ROW_NUMBER()执行此操作:

SELECT  batch_number,
        date_received,
        expiry_date,
        prod_code,
        quantity,
        RowNumber = ROW_NUMBER() 
                        OVER(PARTITION BY batch_number 
                            ORDER BY date_received, expiry_date, prod_code, quantity)
FROM    scheme.stquem

这会给你输出:

batch_number    date_received   expiry_date prod_code   quantity    RowNumber
------------------------------------------------------------------------------
1               2015-08-01      2015-09-01  p1          5           1
1               2015-08-02      2015-08-08  p1          3           2
1               2015-08-02      2015-08-09  p0          1           3

然后您只需将上述查询放入子查询中,并仅为每个分区选择第一行:

SELECT  batch_number, date_received, expiry_date, prod_code, quantity
FROM    (   SELECT  batch_number,
                    date_received,
                    expiry_date,
                    prod_code,
                    quantity,
                    RowNumber = ROW_NUMBER() 
                                    OVER(PARTITION BY batch_number 
                                        ORDER BY date_received, expiry_date, prod_code, quantity)
            FROM    scheme.stquem
        ) AS t
WHERE   t.RowNumber = 1;

因此,您可以获得与最小date_received相关联的字段,而不是与不相关的记录相关联。

答案 1 :(得分:-1)

尝试使用MAX()包装date_received,expiry_date和prod_code,并使用SUM()包装数量。 这有帮助吗?

SELECT batch_number, MAX(date_received), MAX(expiry_date), MAX(prod_code), SUM(quantity) FROM scheme.stquem GROUP BY batch_number