重复行的SQL和值到第一个(或最后一个)

时间:2016-01-21 00:57:09

标签: sql sql-server merge sum duplicates

我想合并重复的行(使用相同的doctype,docnum和item),并将'qtd'列的值与第一个或最后一个值相加。然后删除重复的行,只保留隐藏总值的行。 (删除后的行号不重要,可以不允许顺序号码)

实际上我只有查询来检测重复的行,我需要查询来合并值并删除合并后剩余的重复行。

PS:这是一个很大的表,所以doctype,docnum和item不能在这样的查询中表达...其中doctype ='stket'和docum ='1'和item ='4506'必须找到它们“自动地”

表:docs(带有重复行的首字母)

      doctype  docnum  line    item      qtd
       STKET     1       1   **4506**   10.00
       STKET     1       2     3860     27.00
       STKET     1       3   **4506**    4.00
       STKET     2       1     3860      7.00
       STKET     3       1   **4048**    2.00
       STKET     3       2   **4048**    5.00
       STKET     3       3     4876     11.00
       STKET     4       1     3860      1.00

表:docs(总和后的预期结果)

      doctype  docnum  line    item      qtd
       STKET     1       1     4506   **14.00**
       STKET     1       2     3860     27.00
       STKET     1       3     4506      4.00
       STKET     2       1     3860      7.00
       STKET     3       1     4048    **7.00**
       STKET     3       2     4048      5.00
       STKET     3       3     4876     11.00
       STKET     4       1     3860      1.00

表:docs(删除重复后的预期结果 - 在这种情况下不是第一个!)

      doctype  docnum  line    item      qtd
       STKET     1       1     4506   **14.00**
       STKET     1       2     3860     27.00
       STKET     2       1     3860      7.00
       STKET     3       1     4048    **7.00**
       STKET     3       3     4876     11.00
       STKET     4       1     3860      1.00

[稍后编辑] - 来自“回答”

在ZLK查询之后,我保留了这样的表文档:

  doctype  docnum  line    item      qtd
   STKET     1       1     4506   **10.00**
   STKET     1       2     3860     27.00
   STKET     2       1     3860      7.00
   STKET     3       1     4048    **2.00**
   STKET     3       3     4876     11.00
   STKET     4       1     3860      1.00

它找到重复项和删除项,但不会将已删除行的“qtd”值相加

1 个答案:

答案 0 :(得分:1)

所以我假设您只需要一个基本的更新语句然后删除语句。

UPDATE docs SET qtd = updateqtd
FROM docs d
JOIN (SELECT doctype, docnum, item, MIN(line) line, SUM(qtd) updateqtd
FROM docs
GROUP BY doctype, docnum, item) a ON a.doctype = d.doctype AND a.docnum = d.docnum AND a.item = d.item AND a.line = d.line;

WITH CTE AS (
    SELECT *, ROW_NUMBER() OVER (PARTITION BY doctype, docnum, item ORDER BY line) RN
    FROM docs)
DELETE CTE WHERE RN <> 1

这会更新最低行号,然后删除任何非最低行号。