【问题标题】:How to compare the current month value with last 12 months如何将当前月份值与过去 12 个月进行比较
【发布时间】:2019-07-24 02:46:17
【问题描述】:

我正在尝试将当前月份的值与过去 12 个月的值进行比较。

E.g:
6/30/2019 100
5/31/2019 90
4/30/2019 80
3/31/2019 70
2/8/2019 60
1/31/2019 50
12/31/2018 40
11/30/2018 30
10/31/2018 20
9/30/2018 10
8/31/2018 90
7/30/2018 110

现在当前月份的值(2019 年 6 月 30 日)为 100,然后我想将这些值与过去 12 个月的值进行比较。如果与 12 个月相比,当前月份的值是最大值,那么我想将标志设置为“最大值”。在上面的示例中,110 是最大值,但当前月份为 100,即与过去 12 个月的值相比,它是最小值,然后我想将标志设置为“min”。

另外,我还想获取日期,即,如果它是最小值,那么日期的最大值是多少(预期输出“MIN(110 as on 7/30/2018)”)。

请提供任何解决方案来实现这种情况

预期输出“MIN(截至 2018 年 7 月 30 日为 110)”

【问题讨论】:

  • 什么标志?我认为您需要在此处提供更多详细信息。您要更新数据吗?只需选择数据?我们不能“提供解决方案”,因为您还没有提供整个问题。请参阅 herehere 了解您应该发布的一些想法。
  • 为什么用这种不可靠的不可排序格式而不是ISO-8601?为什么要将输出作为组合字符串而不是两列?
  • 当前月份值是多少(2019 年 6 月 30 日)?应该是属于七月的日期吧?

标签: sql sql-server


【解决方案1】:

如果要将当前值与滚动的 12 个月最小值/最大值进行比较,可以使用窗口函数:

select top (1) t.*,
       (case when value = max12_value then 'MAX'
             when value = min12_value then 'MIN'
        end) as flag
from (select t.*,
             max(value) over (order by date rows between 11 preceding and current row) as max12_value,
             min(value) over (order by date rows between 11 preceding and current row) as min12_value,
      from t
     ) t
order by date desc

【讨论】:

    【解决方案2】:

    如果我理解正确,这是一种方法:

    -- Create a table variable to hold the sample data
    DECLARE @data TABLE (
        [Date] DATE,
        [Value] INT
    )
    
    -- Load the sample data table
    DECLARE @i INT = 0;
    WHILE @i < 12
    BEGIN
        INSERT INTO @data ([Date], [Value]) values (EOMONTH(DATEADD(M,-@i, GETDATE())), FLOOR(RAND()*(100-1+1))+10);
        SET @i = @i + 1;
    END;
    
    -- Select the resulting data set with flags
    WITH t as
    (
    SELECT [Date], [Value], 
        CASE 
            WHEN [Value] = (SELECT MAX([Value]) FROM @data) THEN 'MAX' 
            WHEN [Value] = (SELECT MIN([Value]) FROM @data) THEN 'MIN' 
            ELSE '' 
        END AS Flag 
    FROM @data
    )
    SELECT 'MAX(' + CAST([Value] as VARCHAR(MAX)) + ' as on ' + CAST([Date] as VARCHAR(MAX)) + ')' FROM t WHERE [Flag] = 'MAX'
    

    这将输出:

    MAX(109 as on 2018-09-30)

    将“MIN”替换为“MAX”,您将获得最小值。

    【讨论】:

      【解决方案3】:

      考虑到当前月份的值总是从 GETDATE() 计算出来的,以下脚本将为您提供输出

      WITH CTE (d, value)
      AS
      (
          SELECT id,value FROM your_table
      ),
      CTE2
      AS
      (
          SELECT DISTINCT
          (SELECT Value FROM CTE WHERE d>= CAST(DATEADD(DD,-DATEPART(DD,GETDATE()) + 1,GETDATE())  AS DATE)) current_month_value,
          MIN(value) min_value,
          MAX(value) max_value
          FROM CTE
          WHERE d <  CAST(DATEADD(DD,-DATEPART(DD,GETDATE()) + 1,GETDATE())  AS DATE)
          AND d >= CAST(DATEADD(MM,-13,DATEADD(DD,-DATEPART(DD,GETDATE()) + 1,GETDATE()) ) AS DATE)
      )
      
      SELECT 
      CASE 
          WHEN  current_month_value > max_value THEN 'MAX'
          ELSE 'MIN(' + CAST(max_value AS VARCHAR)+ ' AS ON '+ (SELECT TOP 1 CAST(d AS VARCHAR) FROM CTE WHERE Value = max_value)+ ')'
      END
      FROM CTE2
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2017-11-27
        • 1970-01-01
        相关资源
        最近更新 更多