有没有办法轻松从每月谷物到每日谷物?例如,这是一个月度粮食表:
DECLARE @SessionsPerArea TABLE (idSession INT, startDate DATE)
INSERT @SessionsPerArea VALUES
(1,'2013-01-31'),
(2,'2013-02-28'),
(3,'2013-03-31')
select *
from @SessionsPerArea
结果:
idSession startDate
1 2013-01-01
2 2013-02-01
3 2013-03-01
我希望结果如下:
idSession startDate
1 2013-01-01
1 2013-01-02
1 2013-01-03
.
.
1 2013-01-30
1 2013-01-31
2 2013-02-01
2 2013-02-01
2 2013-02-02
.
.
2 2013-02-27
2 2013-02-28
3 2013-03-01
3 2013-03-02
3 2013-03-03
.
.
3 2013-03-30
3 2013-03-31
答案 0 :(得分:3)
我在 SqlFiddle 上测试了这个例子。它使用recursive Common Table Expression(CTE)创建一个临时结果集,该结果集包含给定idSession
和startDate
的每月中每一天的记录。
;WITH cteDateTable AS
(
SELECT idSession, DATEADD(month, DATEDIFF(month, 0, MIN(startDate) OVER (PARTITION BY idSession)), 0) as StartDate, Max(startDate) OVER (PARTITION BY idSession) as EndDate
FROM SessionsPerArea
UNION ALL
SELECT idSession, DATEADD(D, 1, StartDate), EndDate
FROM cteDateTable
WHERE DATEADD(D, 1, StartDate) <= EndDate
)
SELECT idSession, StartDate
FROM cteDateTable
ORDER BY idSession, StartDate
我得到了一些其他SO答案(以及我浏览的其他人)的帮助。
答案 1 :(得分:0)
如果您使用table of numbers,则简单有效。这是一个很好的article,描述了如何生成它。
对于这个例子,我在运行中填充它,但在生产中我有一个100K行的永久表。它在许多报告中都很有用。
DECLARE @Numbers TABLE (Number int PRIMARY KEY);
INSERT INTO @Numbers (Number)
SELECT TOP(100)
ROW_NUMBER() OVER(ORDER BY sys.all_objects.object_id) AS Number
FROM sys.all_objects;
现在,对于每个会话,我们都会使用CROSS APPLY
返回该月的所有日期。此解决方案会在startDate
之前或之前返回该月的所有日期。如果您的startDate
是该月的最后一天(正如您所说的那样),则该月的每一天都会有一行。
DECLARE @SessionsPerArea TABLE (idSession INT, startDate DATE)
INSERT @SessionsPerArea VALUES
(1,'2013-01-31'),
(2,'2013-02-28'),
(3,'2013-03-31')
SELECT *
FROM
@SessionsPerArea AS S
CROSS APPLY
(
SELECT DATEADD(day, 1-N.Number, S.startDate) AS NewDate
FROM @Numbers AS N
WHERE N.Number <= DAY(S.startDate)
) AS CA
ORDER BY S.idSession, NewDate;
结果集
idSession startDate NewDate
1 2013-01-31 2013-01-01
1 2013-01-31 2013-01-02
1 2013-01-31 2013-01-03
1 2013-01-31 2013-01-04
1 2013-01-31 2013-01-05
1 2013-01-31 2013-01-06
1 2013-01-31 2013-01-07
1 2013-01-31 2013-01-08
1 2013-01-31 2013-01-09
1 2013-01-31 2013-01-10
1 2013-01-31 2013-01-11
1 2013-01-31 2013-01-12
1 2013-01-31 2013-01-13
1 2013-01-31 2013-01-14
1 2013-01-31 2013-01-15
1 2013-01-31 2013-01-16
1 2013-01-31 2013-01-17
1 2013-01-31 2013-01-18
1 2013-01-31 2013-01-19
1 2013-01-31 2013-01-20
1 2013-01-31 2013-01-21
1 2013-01-31 2013-01-22
1 2013-01-31 2013-01-23
1 2013-01-31 2013-01-24
1 2013-01-31 2013-01-25
1 2013-01-31 2013-01-26
1 2013-01-31 2013-01-27
1 2013-01-31 2013-01-28
1 2013-01-31 2013-01-29
1 2013-01-31 2013-01-30
1 2013-01-31 2013-01-31
2 2013-02-28 2013-02-01
2 2013-02-28 2013-02-02
2 2013-02-28 2013-02-03
2 2013-02-28 2013-02-04
2 2013-02-28 2013-02-05
2 2013-02-28 2013-02-06
2 2013-02-28 2013-02-07
2 2013-02-28 2013-02-08
2 2013-02-28 2013-02-09
2 2013-02-28 2013-02-10
2 2013-02-28 2013-02-11
2 2013-02-28 2013-02-12
2 2013-02-28 2013-02-13
2 2013-02-28 2013-02-14
2 2013-02-28 2013-02-15
2 2013-02-28 2013-02-16
2 2013-02-28 2013-02-17
2 2013-02-28 2013-02-18
2 2013-02-28 2013-02-19
2 2013-02-28 2013-02-20
2 2013-02-28 2013-02-21
2 2013-02-28 2013-02-22
2 2013-02-28 2013-02-23
2 2013-02-28 2013-02-24
2 2013-02-28 2013-02-25
2 2013-02-28 2013-02-26
2 2013-02-28 2013-02-27
2 2013-02-28 2013-02-28
3 2013-03-31 2013-03-01
3 2013-03-31 2013-03-02
3 2013-03-31 2013-03-03
3 2013-03-31 2013-03-04
3 2013-03-31 2013-03-05
3 2013-03-31 2013-03-06
3 2013-03-31 2013-03-07
3 2013-03-31 2013-03-08
3 2013-03-31 2013-03-09
3 2013-03-31 2013-03-10
3 2013-03-31 2013-03-11
3 2013-03-31 2013-03-12
3 2013-03-31 2013-03-13
3 2013-03-31 2013-03-14
3 2013-03-31 2013-03-15
3 2013-03-31 2013-03-16
3 2013-03-31 2013-03-17
3 2013-03-31 2013-03-18
3 2013-03-31 2013-03-19
3 2013-03-31 2013-03-20
3 2013-03-31 2013-03-21
3 2013-03-31 2013-03-22
3 2013-03-31 2013-03-23
3 2013-03-31 2013-03-24
3 2013-03-31 2013-03-25
3 2013-03-31 2013-03-26
3 2013-03-31 2013-03-27
3 2013-03-31 2013-03-28
3 2013-03-31 2013-03-29
3 2013-03-31 2013-03-30
3 2013-03-31 2013-03-31