【问题标题】:SQL Cumulative CountSQL 累积计数
【发布时间】:2013-10-14 13:26:46
【问题描述】:

我有部门的桌子。我需要计算有多少人在哪个部门。这很容易通过

SELECT DEPT,
       COUNT(*) as 'Total'
    FROM SR
    GROUP BY DEPT;

现在我还需要做如下累积计数:

我找到了一些 SQL 来计算运行总数,但不是这样的情况。在这种情况下,您能给我一些建议吗?

【问题讨论】:

  • 你可以添加你的表的架构还是你有任何主键??
  • 我猜您在输入问题时并未向您提供此线程。 stackoverflow.com/questions/860966/… 顺便说一句,我的谷歌搜索字符串是“sql server running totals”。
  • @Dhaval - 没有 PK 也没有行号,因为数据正在通过 SCD 进行历史记录。
  • 如果你不知道“running total”这个词,你可以很好地搜索“sql server累积计数”,这会给你大量的建议好吧。

标签: sql sql-server sql-server-2008


【解决方案1】:

这是一种使用 CTE 而不是光标的方法:

WITH Base AS
(
    SELECT ROW_NUMBER() OVER (ORDER BY [Count] DESC) RowNum,
    [Dept],
    [Count]
    FROM SR
)
SELECT SR.Dept, SR.Count, SUM(SR2.[Count]) Total
FROM Base SR
INNER JOIN Base SR2
    ON SR2.RowNum <= SR.RowNum
GROUP BY SR.Dept, SR.Count
ORDER BY SR.[Count] DESC

请注意,这是按Count 降序排列的,就像您的示例结果一样。如果还有其他未显示的列应该用于排序,只需在每个 ORDER BY 子句中替换 Count

SQL Fiddle Demo

【讨论】:

  • 太好了,这非常适合我的需要。是否还有可能“轻松”在累积计数旁边添加另一个派生列,这将计算每行的 (cumulative_count / sum [per_all_depts])?在cumulative_count / 254的意思。结果应该显示为百分比。
  • 完成了,我自己找到的。再次感谢,感谢您的帮助!
【解决方案2】:

我认为您可以为此使用一些临时/变量表,并使用来自here 的解决方案:

declare @Temp table (rn int identity(1, 1) primary key, dept varchar(128), Total int)

insert into @Temp (dept, Total)
select
    dept, count(*) as Total
from SR
group by dept

;with cte as (
    select T.dept, T.Total, T.Total as Cumulative, T.rn
    from @Temp as T
    where T.rn = 1
    union all
    select T.dept, T.Total, T.Total + C.Cumulative as Cumulative, T.rn
    from cte as C
        inner join @Temp as T on T.rn = C.rn + 1
)
select C.dept, C.Total, C.Cumulative
from cte as C
option (maxrecursion 0)

sql fiddle demo

还有其他一些解决方案,但我认为这个对于 SQL Server 2008 来说是最快的。

【讨论】:

  • @ypercube 不错的文章,谢谢,但实际上,在这篇文章中,游标方法比 CTE 慢 2 倍(但它的 I/O 操作更少)
  • 是的,没错,我看错了图片。我确信(在我的记忆中)情况正好相反。也许我放弃了 CTE 方法,因为它需要连续的数字(您可以通过临时表和 IDENTITY 获得)。再次链接到这些 cmets 中讨论的文章:Best approaches for running totals.
  • @ypercube 是的,cte 的代码比光标少一点,但它需要数字/其他键而没有间隙
猜你喜欢
  • 2020-10-08
  • 1970-01-01
  • 1970-01-01
  • 2021-09-01
  • 1970-01-01
  • 2022-08-04
  • 1970-01-01
  • 2017-04-17
  • 2019-07-03
相关资源
最近更新 更多