【问题标题】:Cumulated Count by Week每周累计计数
【发布时间】:2020-03-04 09:28:04
【问题描述】:

目前我使用 MySQL - 但很快就会迁移到 SQL Server - 所以两者都可以解决问题!

我有一个像(候选表)这样的数据库架构:

ID int PRIMARYKEY
intern date
name varchar(255)

表格看起来像:

| ID         | intern          |   name    |
+------------+-----------------+-----------+
| 1          |  '2020-01-02'   |   Mike    |
| 42         |  '2020-01-05'   |   Nora    |
| 21         |  '2020-01-08'   |   Iris    |
| 331        |  '2020-01-12'   |   Caro    |

以及该表中的其他一些不相关的列。

我想按周计算所有实习生日期。这适用于:

SELECT 
    WEEK(intern) + 1 AS KW, COUNT(intern) AS counts
FROM 
    epunkt_sourcing.candidate
WHERE 
    WEEK(intern) IS NOT NULL AND YEAR(intern) = 2020
GROUP BY 
    KW
ORDER BY 
    KW;

结果是这样的:

| KW        | counts          |
+-----------+-----------------+
| 1         |  2              |
| 2         | 19              |
| 3         | 18              |
| 4         | 21              |

我还想要按周累积的计数,有机会求和吗?

| KW        | counts          | cumulated   |
+-----------+-----------------+-------------+
| 1         |  2              |  2          |
| 2         | 19              | 21          |
| 3         | 18              | 39          |
| 4         | 21              | 60          |

【问题讨论】:

  • MySQL 还是 SQL Server?你已经标记了两者?
  • 我目前使用 mysql - 但在接下来的几周内迁移到 sql server - 所以两者都适合解决方案
  • 目前我使用 MySQL 什么版本?这对您的问题至关重要。
  • ... 并提供一些示例小提琴(并显示小提琴数据的所需结果,而不是抽象数据)。
  • 这个MySQL版本的累积和是使用2个表副本或使用用户定义的变量来实现的。在存在SUM() OVER () 的SQL Server 中使用时,这两种方法都必须完全重写。如果您将迁移到 SQL Server - 将您的 MySQL 更新到最新 (8.0.19) 版本。

标签: mysql sql sql-server


【解决方案1】:

请尝试以下查询,希望对您有所帮助:

SELECT t.KW, t.counts, @cum_total:=@cum_total + t.counts AS cumulative_sum
    FROM
        ( 
            SELECT WEEK(intern)+1 as KW, count(intern) as counts
                FROM epunkt_sourcing.candidate
            WHERE WEEK(intern) IS NOT NULL AND YEAR(intern) = 2020
            GROUP BY WEEK(intern)
        ) AS t
    JOIN (SELECT @cum_total:=0) r;

【讨论】:

    【解决方案2】:

    我认为这应该可行。不确定它是否最有效。

        SELECT WEEK(intern)+1 as KW, count(intern) as counts into #tempCount
        from epunkt_sourcing.candidate
        WHERE WEEK(intern) IS NOT NULL AND YEAR(intern) = 2020
        GROUP BY WEEK(intern)
    
        select
         a.kw
        ,a.counts
        ,sum(b.counts) as cumulated
    
        from #tempCount a
        inner join #tempCount b on a.kw >= b.kw
    
        group by a.kw, a.counts
        order by a.kw
    
    

    请测试一下并告诉我

    【讨论】:

      【解决方案3】:

      在 MySQL 和 SQL Server 中,您应该使用累积和。 MySQL版本是:

      SELECT WEEK(intern)+1 as KW, COUNT(*) as counts,
            SUM(COUNT(*)) OVER (ORDER BY MIN(intern)) as cumulative
      FROM epunkt_sourcing.candidate
      WHERE intern >= '2020-01-01' AND intern < '2021-01-01'
      GROUP BY KW
      ORDER BY KW;
      

      在 SQL Server 中,您将使用:

      SELECT DATE_PART(WEEK, intern)+1 as KW, COUNT(*) as counts,
            SUM(COUNT(*)) OVER (ORDER BY MIN(intern)) as cumulative
      FROM epunkt_sourcing.candidate
      WHERE intern >= '2020-01-01' AND intern < '2021-01-01'
      GROUP BY DATE_PART(WEEK, intern)+1 
      ORDER BY KW;
      

      注意事项:

      • 第一周可能是部分周,具体取决于年份。周从星期一开始,但年份可以从任何日期开始。
      • 年份的比较使用日期不等式。在两个数据库中都建议这样做。
      • 日期部分函数因数据库而异。
      • SQL Server 不允许在 GROUP BY 中使用列别名。
      • 两个数据库都支持窗口函数。 MySQL 支持变量,但它们现在已被弃用,因此您不应该使用它们。

      【讨论】:

        【解决方案4】:

        你可以在 SQL Server 中试试这个:

        Declare @t table  (KW int,counts int)
        
        Insert into @t values (1,2),(2,19),(3,18),(4,21)
        
        select *, sum(counts) over (order by kw) as cumulated 
        from @t
        

        输出:

        KW  counts  cumulated  
        1     2           2  
        2     19         21  
        3     18         39  
        4     21         60  
        

        【讨论】:

          猜你喜欢
          • 2018-02-11
          • 1970-01-01
          • 2021-09-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2021-08-05
          相关资源
          最近更新 更多