我现在有这个SQL:
CREATE PROCEDURE dbo.sel_Track_HitsLast30Days(
@projectID int
)
AS
BEGIN
DECLARE @FirstDay smalldatetime, @NumberOfMonths int, @priorMonth smalldatetime
set @priorMonth = (SELECT CAST(
(
STR( YEAR( dateadd(m,-1, getDate()) ) ) + '/' +
STR( MONTH( dateadd(m,-1, getDate()) ) ) + '/' +
STR( DAY( dateadd(m,-1, getDate()) ) )
)
AS DateTime
))
Select @FirstDay = @priorMonth, @NumberOfMonths = 1
;WITH Days AS (
SELECT @FirstDay as CalendarDay
UNION ALL
SELECT DATEADD(d, 1, CalendarDay) as CalendarDay
FROM Days
WHERE DATEADD(d, 1, CalendarDay) < DATEADD(m, @NumberOfMonths, @FirstDay+1)
)
SELECT calendarday,foundDate.TotalbyDate,foundDate.date FROM Days
LEFT OUTER JOIN (
SELECT
COUNT(LEFT(visitDateTime, 11)) AS TotalbyDate,substring(convert( char(10), CONVERT( char(10), visitDateTime, 121 ) ), 1, 11) AS date
FROM
dbo.TrackingData
WHERE
visitDateTime >= dateadd(d, datediff(d, 0, getdate()), -30) and projectID = @projectID
GROUP BY substring(convert( char(10), CONVERT( char(10), visitDateTime, 121 ) ), 1, 11)
) foundDate on foundDate.date = CalendarDay
order by
CalendarDay Desc
END
这项工作正常,但是没有考虑到31天的月份,而且由于某种原因我没有回到今天的日期。
答案 0 :(得分:1)
尝试此操作(使用AdventureWorks作为示例数据库)
DECLARE @today datetime, @NumberOfMonths int, @FirstDay smalldatetime
SELECT @today = '2004-03-09', -- getdate(), tests only
@NumberOfMonths = 1,
@FirstDay = CAST(FLOOR(CAST(
DATEADD(M, -1, @today) AS float)) AS datetime);
WITH Days AS
(
SELECT @FirstDay AS CalendarDay UNION ALL
SELECT DATEADD(d, 1, CalendarDay) AS CalendarDay FROM Days
WHERE DATEADD(d, 1, CalendarDay) < DATEADD(m, @NumberOfMonths, @FirstDay+1)
)
SELECT CONVERT(varchar(10), CalendarDay, 111) as [Date],
COUNT(TransactionDate) as [Count]
FROM Days LEFT JOIN Production.TransactionHistory
ON TransactionDate = Days.CalendarDay
GROUP BY CalendarDay
ORDER BY CalendarDay
将输出
Date Count ---------- ----------- 2004/02/09 272 2004/02/10 308 2004/02/11 264 2004/02/12 265 2004/02/13 250 ...
编辑:已更新,以包含所有间隔日期
答案 1 :(得分:0)
HEre是Ruben答案的修改版本:
DECLARE @today DATETIME,
@firstDayLastMonth DATETIME,
@daysCount int
SET @today = getDate()
SET @firstDayLastMonth = Dateadd(m,-1,Dateadd(d,-Day(@today) + 1,@today))
Set @daysCount = (select datepart(dd,dateadd(dd,-1,dateadd(mm,1,cast(cast(year(@firstDayLastMonth) as varchar)+'-'+cast(month(@firstDayLastMonth) as varchar)+'-01' as datetime)))))
SELECT substring(convert( char(10), CONVERT( char(10), visitDateTime, 121 ) ), 1, 11) AS [Date], Count(* ) AS [Count]
FROM dbo.TrackingData
WHERE visitdatetime >= Dateadd(d,-@daysCount,@today)
GROUP BY substring(convert( char(10), CONVERT( char(10), visitDateTime, 121 ) ), 1, 11)
ORDER BY substring(convert( char(10), CONVERT( char(10), visitDateTime, 121 ) ), 1, 11)
答案 2 :(得分:0)
好的,我明白了。鲁本斯给了我一个主意,所以我修改了我的SQL:
DECLARE @FirstDay SMALLDATETIME,
@NumberOfMonths INT,
@priorMonth SMALLDATETIME,
@firstDayLastMonth DateTime,
@daysCount int
set @firstDayLastMonth = dateadd(m, -1, dateadd(d, -day(getDate()) + 1, getDate()))
set @daysCount = (select datepart(dd,dateadd(dd,-1,dateadd(mm,1,cast(cast(year(@firstDayLastMonth) as varchar)+'-'+cast(month(@firstDayLastMonth) as varchar)+'-01' as datetime)))))
SET @priorMonth = (SELECT Cast((Str(Year(Dateadd(m,-1,Getdate()))) + '/' + Str(Month(Dateadd(m,-1,Getdate()))) + '/' + Str(Day(Dateadd(m,-1,Getdate())))) AS DATETIME))
Declare @before dateTime
Set @before = Dateadd(d,-@daysCount,getdate())
SELECT @FirstDay = @before,
@NumberOfMonths = 1;
WITH days
AS (SELECT @FirstDay AS calendarday
UNION ALL
SELECT Dateadd(d,1,calendarday) AS calendarday
FROM days
WHERE Dateadd(d,1,calendarday) <= Dateadd(m,@NumberOfMonths,@FirstDay))
SELECT Substring(Convert(CHAR(10),Convert(CHAR(10),calendarday,101)),
1,11) ,
founddate.totalbydate,
founddate.DATE
FROM days
LEFT OUTER JOIN (SELECT Count(Left(visitdatetime,11)) AS totalbydate,
Substring(Convert(CHAR(10),Convert(CHAR(10),visitdatetime,101)),
1,11) AS DATE
FROM dbo.trackingdata
WHERE visitdatetime >= Dateadd(d,Datediff(d,0,Getdate()),-29)
AND projectid = 131
GROUP BY Substring(Convert(CHAR(10),Convert(CHAR(10),visitdatetime,101)),
1,11)) founddate
ON founddate.DATE = Substring(Convert(CHAR(10),Convert(CHAR(10),calendarday,101)),
1,11)