【问题标题】:How to Convert a Date Span to Monthly Records using SQL如何使用 SQL 将日期跨度转换为每月记录
【发布时间】:2023-01-10 12:36:26
【问题描述】:

我在几个月内为用户设置了多个日期跨度,我想按月和年(默认为每月的第一天)将每个跨度拆分为多行,用户在跨度期间一直处于活动状态。活跃用户将有未来的结束日期记录被拆分到当前月份和年份

现有数据

ID Start date end date
1234 2019-01-01 2019-03-31
1234 2019-09-18 2020-01-31
1234 2022-11-15 2025-01-31

试图将以下日期月份查询放入跨度中

  Select Top 500 mmdd=cast (dateadd(Month,-1+Row_Number() Over (Order By (Select NULL)),'2019-01-01') as date)
  
          From master..spt_values n1 
          order by 1 asc

预期产出

ID active month
1234 2019-01-01
1234 2019-02-01
1234 2019-03-01
1234 2019-09-01
1234 2019-10-01
1234 2019-11-01
1234 2019-12-01
1234 2020-01-01
1234 2022-11-01
1234 2022-12-01
1234 2023-01-01

【问题讨论】:

  • 投资日历表

标签: sql sql-server


【解决方案1】:

Larnu 走在正确的轨道上。我发现的最简单的方法之一是创建一个日历表或一个函数(它们可以有效地做同样的事情)。

尝试这个:

CREATE FUNCTION [dbo].[udfCalendar] 
(   
   @StartDate Date,
   @EndDate Date
)
RETURNS @Calendar TABLE (ID int, DateValue DateTime, DayValue int, MonthValue int, YearValue int)
AS

BEGIN
   WHILE @StartDate < @EndDate
   BEGIN
       INSERT @Calendar
       SELECT --like 20190101, 1/1/2019, 1, 1, 2019
           YEAR (@StartDate) * 10000 + MONTH (@StartDate) * 100 + Day (@StartDate) AS ID,
           @StartDate AS DateValue,
           DATEPART (dd, @StartDate) AS DayValue,
           DATEPART (mm, @StartDate) AS MonthValue,
           DATEPART (yy, @StartDate) AS YearValue;
    
       SET @StartDate = DateAdd(m, 1, @StartDate);
   END

   RETURN;
END

然后你可以加入它

Select n1.ID, cal.DateValue as ActiveMonth
From master..spt_values n1 inner join 
    dbo.udfCalendar('1/1/2019', '1/1/2023') cal 
    On cal.DateValue Between n1.StartDate and n1.EndDate
Order By DateValue

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-12-06
    • 1970-01-01
    • 1970-01-01
    • 2018-03-22
    • 2023-03-24
    相关资源
    最近更新 更多