我有一个日期时间字段,我希望在日期范围内从小时8:00到9:00按日计算所有记录(即:从:01/01/2012到:01/03/2012)。
例如,如果我有以下数据:
2012-01-01 08:26
2012-01-01 08:40
2012-01-01 09:26
2012-01-01 10:26
2012-01-02 08:06
2012-01-02 09:26
2012-01-02 09:40
2012-01-03 08:30
2012-01-03 10:26
结果应如下所示:
2012-01-01 2
2012-01-02 1
2012-01-03 1
编辑: 以下是我使用@gbn解决方案(它适用于我)
SELECT COUNT(*), convert(varchar(10),ScanDate,101)
FROM tblSingleBox (nolock)
WHERE DATEPART(Hour, scandate) = 8
and (scandate>='01/03/2012' and scandate<'01/05/2012')
GROUP BY convert(varchar(10),ScanDate,101)
order by convert(varchar(10),ScanDate,101)
答案 0 :(得分:4)
SQL Server 2005及更早版本
SELECT
COUNT(*),
DATEADD(dd, DATEDIFF(dd, 0, SomeDateTime), 0)
-- SQL Server 2008: CAST(SomeDateTime AS date)
FROM
SomeTable
WHERE
DATEPART(Hour, SomeDateTime) = 8
GROUP BY
DATEADD(dd, DATEDIFF(dd, 0, SomeDateTime), 0);
-- SQL Server 2008: CAST(SomeDateTime AS date);
MySQL的:
SELECT
COUNT(*),
DATE(SomeDateTime)
FROM
SomeTable
WHERE
HOUR(SomeDateTime) = 8
GROUP BY
DATE(SomeDateTime);
答案 1 :(得分:2)
在这种情况下,最简单的代码和最快的代码可能会有很大差异,并且可能取决于数据集的大小。
我怀疑最快的是加入日历和过滤器。在这种情况下,我会在开始之前制作日历,但我建议使用永久日历...
CREATE TABLE #calendar (
date AS DATETIME
)
INSERT INTO #calendar SELECT '2011-12-31' UNION ALL SELECT '2012-01-01'
UNION ALL SELECT '2012-01-02' UNION ALL SELECT '2012-01-03'
UNION ALL SELECT '2012-01-04' UNION ALL SELECT '2012-01-05'
SELECT
calendar.date,
COUNT(*)
FROM
yourTable
INNER JOIN
#calendar AS calendar
ON yourTable.DateTimeField >= calendar.date + @minTime
AND yourTable.DateTimeField < calendar.date + @maxTime
WHERE
calendar.date >= @startDate
AND calendar.date <= @endDate
GROUP BY
calendar.date
这应该产生最友好的索引查询,因此对于任何合理大小的数据都非常有效。
注意:强>
calendar.date + @Time
部分会有所不同。你刚刚说过MS SQL Server,所以它更像是......
ON yourTable.DateTimeField >= DATEADD(hour, @minHour, calendar.date)
AND yourTable.DateTimeField < DATEADD(hour, @maxHour, calendar.date)
答案 2 :(得分:0)
SQL Server 2005
IF OBJECT_ID('tempdb.dbo.#DATES') IS NOT NULL
DROP TABLE #DATES
CREATE TABLE #DATES
( LogDate smalldatetime )
INSERT INTO #DATES
( LogDate )
SELECT '2012-01-01 08:26'
UNION SELECT '2012-01-01 08:40'
UNION SELECT '2012-01-01 09:26'
UNION SELECT '2012-01-01 10:26'
UNION SELECT '2012-01-02 08:06'
UNION SELECT '2012-01-02 09:26'
UNION SELECT '2012-01-02 09:40'
UNION SELECT '2012-01-03 08:30'
UNION SELECT '2012-01-03 10:26'
UNION SELECT '2012-01-03 15:26'
DECLARE @nStartHour smallint
DECLARE @nEndHour smallint
SET @nStartHour = 15
SET @nEndHour = 16
SELECT CONVERT(varchar, LogDate, 101), COUNT(*)
FROM #DATES
WHERE DATEPART(hour,LogDate) BETWEEN @nStartHour AND (@nEndHour - 1)
GROUP BY CONVERT(varchar, LogDate, 101)