Sql server Sql Server:每十分钟计数一次记录(包括零)

Sql server Sql Server:每十分钟计数一次记录(包括零),sql-server,sql-server-2005,Sql Server,Sql Server 2005,我目前有一个表(SQLServer2005),记录我的web应用程序的访问,我想整理一些代码来报告(并显示可视化)流量。我想要的是显示过去24小时内每十分钟的访问次数 我有一个查询就是这样做的,但是有十分钟的时间间隔,在此期间没有访问,我想调整我的查询以显示这些时间间隔的零计数。我想我可以想出一些使用游标的方法,但如果我能避免的话,我宁愿不使用它们 以下是到目前为止的查询: DECLARE @time int DECLARE @interval int SELECT @time=96 SELEC

我目前有一个表(SQLServer2005),记录我的web应用程序的访问,我想整理一些代码来报告(并显示可视化)流量。我想要的是显示过去24小时内每十分钟的访问次数

我有一个查询就是这样做的,但是有十分钟的时间间隔,在此期间没有访问,我想调整我的查询以显示这些时间间隔的零计数。我想我可以想出一些使用游标的方法,但如果我能避免的话,我宁愿不使用它们

以下是到目前为止的查询:

DECLARE @time int
DECLARE @interval int
SELECT @time=96
SELECT @interval=10
SELECT interval,
COUNT(*) AS requestCount,
DATEDIFF(MINUTE,DATEADD(HOUR,-1*@time-1,getDate()),interval)/@interval AS intervalPos
FROM 
(SELECT DATEADD(MINUTE, FLOOR(DATEDIFF(MINUTE, getDate(), requestBegin) / (@interval*1.0)) * @interval,getDate())
FROM [track_pageSubmit] WHERE requestBegin IS NOT NULL AND DATEDIFF(HOUR,requestBegin,getDate()) < @time) AS I(interval) 
GROUP BY interval ORDER BY interval
下面是一些记录的样子:

插入到track_pageSubmit(popid、节、页、请求开始、请求结束、呈现、后开始、后结束)
选择'2393712','Main_Can_Eng','10','2010-01-22 10:22:08.287','2010-01-22 10:22:08.330',空值,'2010-01-22 10:22:09.503','2010-01-22 10:22:09.627'UNION
选择“2393712”、“Main_canu_Eng”、“11”、“2010-01-22 10:22:09.660”、“2010-01-22 10:22:09.770”、“空”、“2010-01-22 10:22:10.973”、“2010-01-22 10:22:11.050”
选择'2393712','Main_Can_Eng','12','2010-01-22 10:22:11.080','2010-01-22 10:22:11.143',空值,'2010-01-22 10:22:12.503','2010-01-22 10:22:12.567'UNION
选择“2394478”、“main”、“21”、“2010-01-21 10:38:54.057”、“2010-01-21 10:38:54.117”、“2010-01-21 10:38:54.487”、“2010-01-21 10:38:55.633”、“2010-01-21 10:38:55.697”
选择“2394478”、“main”、“22”、“2010-01-21 10:38:55.757”、“2010-01-21 10:38:55.820”、“2010-01-21 10:38:56.197”、“2010-01-21 10:38:57.477”、“2010-01-21 10:38:57.570”
选择“2394478”、“main”、“23”、“2010-01-21 10:38:57.617”、“2010-01-21 10:38:57.993”、“2010-01-21 10:38:58.367”、“2010-01-21 10:38:59.397”、“2010-01-21 10:38:59.493”
选择“2394478”、“main”、“25”、“2010-01-21 10:38:59.553”、“2010-01-21 10:38:59.617”、“2010-01-21 10:38:59.993”、“2010-01-21 10:39:01.227”和“2010-01-21 10:39:01.303”
选择'2394478'、'main'、'26'、'2010-01-21 10:39:01.350'、'2010-01-21 10:39:01.477'、'2010-01-21 10:39:01.860'、'2010-01-21 10:39:02.787'、'2010-01-21 10:39:02.867'组合
选择“2394478”、“main”、“27”、“2010-01-21 10:39:02.930”、“2010-01-21 10:39:03.007”、“2010-01-21 10:39:03.400”、“2010-01-21 10:39:04.147”、“2010-01-21 10:39:04.460”
选择'2394478'、'main'、'28'、'2010-01-21 10:39:04.507'、'2010-01-21 10:39:05.147'、'2010-01-21 10:39:05.790'、'2010-01-21 10:39:19.413'、'2010-01-21 10:39:19.477'联合
选择“2393754”,“exp46_cex”,“1”,“2010-01-22 12:40:56.563”,“2010-01-22 12:40:56.640”,空,“2010-01-22 12:40:58.657”,“2010-01-22 12:40:58.733”联合
选择“2393754”,“exp46_cex”,“2”,“2010-01-22 12:40:58.750”,“2010-01-22 12:40:58.780”,空,“2010-01-22 12:41:15.623”,“2010-01-22 12:41:15.657”联合
选择“2393754”,“附加注释”,“1”,“2010-01-22 12:41:15.670”,“2010-01-22 12:41:15.733”,空,“2010-01-22 12:41:19.000”,“2010-01-22 12:41:19.030”联合
选择“2393802”、“main”、“2”、“2010-01-22 12:44:50.857”、“2010-01-22 12:44:50.933”、“空”、“2010-01-22 12:44:53.497”、“2010-01-22 12:44:53.557”联合
选择“2393802”、“main”、“3”、“2010-01-22 12:44:53.590”、“2010-01-22 12:44:53.667”、“空”、“2010-01-22 12:44:56.370”、“2010-01-22 12:44:56.730”

任何可以更改查询的人都可以获得额外的积分(以我的额外感谢的形式),这样我就可以在每个时间间隔(除了总请求之外)报告不同的POPID


谢谢

实现这一点的简单方法是使用CTE并创建一个具有开始时间间隔的帮助表,然后在主查询中使用between连接到该表

这有意义吗?稍后我将编写一些示例代码

DECLARE @time int
DECLARE @interval int
SELECT @time=96
SELECT @interval=10

DECLARE @count int
SELECT @count=1

;WITH daterange AS
(
   SELECT 1 as [id], Max(requestbegin) as maxr, Min(requestBegin) as minr
   FROM track_pagesubmit
), intervals as
(
   SELECT @count AS interval, minr as intervalpos
   FROM daterange
   WHERE [id] = 1
   UNION ALL
   SELECT interval+1 AS interval,
          DATEADD(MINUTE,@interval,intervalpos) as intervalpos
   FROM intervals
   JOIN daterange on [ID] = 1
   WHERE DATEADD(MINUTE,@interval,intervalpos) < maxr
)
SELECT interval, intervalpos, 
       COUNT(DISTINCT track_pagesubmit.popid) as popcount,
       COUNT(track_pagesubmit.id AS requestcount 
FROM intervals
LEFT JOIN track_pagesubmit ON requestbegin IS NOT NULL 
  AND requestBegin BETWEEN intervalpos AND DATEADD(ns,-1,DATEADD(MINUTE,@interval,intervalpos))
GROUP BY interval, intervalpos 
OPTION (MAXRECURSION 200)
DECLARE@time int
声明@interval int
选择@time=96
选择@interval=10
声明@countint
选择@count=1
;日期范围为
(
选择1作为[id],选择Max(requestbegin)作为maxr,选择Min(requestbegin)作为minr
从跟踪页面提交
),间隔为
(
选择@count作为间隔,minr作为间隔pos
从日期范围
其中[id]=1
联合所有
选择间隔+1作为间隔,
日期添加(分钟、间隔、间隔)为间隔位置
每隔一段时间
[ID]=1上的联接日期范围
其中DATEADD(分钟、间隔、间隔)
实现这一点的简单方法是使用CTE并创建一个带有开始时间间隔的帮助表,然后在主查询中使用between连接到该表

这有意义吗?稍后我将编写一些示例代码

DECLARE @time int
DECLARE @interval int
SELECT @time=96
SELECT @interval=10

DECLARE @count int
SELECT @count=1

;WITH daterange AS
(
   SELECT 1 as [id], Max(requestbegin) as maxr, Min(requestBegin) as minr
   FROM track_pagesubmit
), intervals as
(
   SELECT @count AS interval, minr as intervalpos
   FROM daterange
   WHERE [id] = 1
   UNION ALL
   SELECT interval+1 AS interval,
          DATEADD(MINUTE,@interval,intervalpos) as intervalpos
   FROM intervals
   JOIN daterange on [ID] = 1
   WHERE DATEADD(MINUTE,@interval,intervalpos) < maxr
)
SELECT interval, intervalpos, 
       COUNT(DISTINCT track_pagesubmit.popid) as popcount,
       COUNT(track_pagesubmit.id AS requestcount 
FROM intervals
LEFT JOIN track_pagesubmit ON requestbegin IS NOT NULL 
  AND requestBegin BETWEEN intervalpos AND DATEADD(ns,-1,DATEADD(MINUTE,@interval,intervalpos))
GROUP BY interval, intervalpos 
OPTION (MAXRECURSION 200)
DECLARE@time int
声明@interval int
选择@time=96
选择@interval=10
声明@countint
选择@count=1
;日期范围为
(
选择1作为[id],选择Max(requestbegin)作为maxr,选择Min(requestbegin)作为minr
从跟踪页面提交
),间隔为
(
选择@count作为间隔,minr作为间隔pos
从日期范围
其中[id]=1
联合所有
选择间隔+1作为间隔,
日期添加(分钟、间隔、间隔)为间隔位置
每隔一段时间
[ID]=1上的联接日期范围
其中DATEADD(分钟、间隔、间隔)
递归CTE似乎总是优于数字表,但传统上用于此目的。

递归CTE似乎总是优于数字表,但传统上用于此目的。

--因为示例数据跨越27小时:

DECLARE
    @hours TINYINT,
    @minute_interval TINYINT,
    @start SMALLDATETIME;

SELECT
    @hours = 27,
    @minute_interval = 10,
    @start = '20100122 13:00';

;WITH x AS 
(
    SELECT TOP (@hours * (60 / @minute_interval))
        n = ROW_NUMBER() OVER
        (ORDER BY column_id)
    FROM msdb.sys.columns
),
intervals(boundary) AS
(
    SELECT CONVERT
    (
      SMALLDATETIME,
      DATEADD(MINUTE, (-n * @minute_interval), @start)
    )
    FROM x
)
SELECT
    i.boundary,
    RequestCount = COUNT(d.id),
    DistinctPopIDs = COUNT(DISTINCT d.popid)
FROM
    intervals AS i
LEFT OUTER JOIN
    dbo.Track_PageSubmit AS d
    ON d.requestBegin >= i.boundary
    AND d.requestBegin < DATEADD(MINUTE, @minute_interval, i.boundary)
GROUP BY i.boundary
ORDER BY i.boundary;
声明
@小时T
DECLARE
    @hours TINYINT,
    @minute_interval TINYINT,
    @start SMALLDATETIME;

SELECT
    @hours = 27,
    @minute_interval = 10,
    @start = '20100122 13:00';

;WITH x AS 
(
    SELECT TOP (@hours * (60 / @minute_interval))
        n = ROW_NUMBER() OVER
        (ORDER BY column_id)
    FROM msdb.sys.columns
),
intervals(boundary) AS
(
    SELECT CONVERT
    (
      SMALLDATETIME,
      DATEADD(MINUTE, (-n * @minute_interval), @start)
    )
    FROM x
)
SELECT
    i.boundary,
    RequestCount = COUNT(d.id),
    DistinctPopIDs = COUNT(DISTINCT d.popid)
FROM
    intervals AS i
LEFT OUTER JOIN
    dbo.Track_PageSubmit AS d
    ON d.requestBegin >= i.boundary
    AND d.requestBegin < DATEADD(MINUTE, @minute_interval, i.boundary)
GROUP BY i.boundary
ORDER BY i.boundary;
WITH Nbrs_2( n ) AS ( SELECT 1 UNION SELECT 0 ),
    Nbrs_1( n ) AS ( SELECT 1 FROM Nbrs_2 n1 CROSS JOIN Nbrs_2 n2 ),
    Nbrs_0( n ) AS ( SELECT 1 FROM Nbrs_1 n1 CROSS JOIN Nbrs_1 n2 ),
    Nbrs  ( n ) AS ( SELECT 1 FROM Nbrs_0 n1 CROSS JOIN Nbrs_0 n2 )
select n.n as TenMinuteInterval, count(case when t.requestBegin is null then null else 1 end) as Count
from (
    SELECT n - 1 as n
    FROM (SELECT ROW_NUMBER()  OVER (ORDER BY n)
    FROM Nbrs) D ( n )
    WHERE n <= 144
) n
left outer join track_pageSubmit t on n.n = floor((cast(requestBegin - convert(int, requestBegin) as decimal(10,3)) % 1) * 144) 
    and requestBegin between '2010-01-21' and '2010-01-22'
group by n.n
TenMinuteInterval Count
-----------------------
0                  0
1                  0
2                  0
3                  0
4                  0
5                  0
6                  0
7                  0
8                  0
9                  0
10                 0
11                 0
12                 0
13                 0
14                 0
15                 0
16                 0
17                 0
18                 0
19                 0
20                 0
21                 0
22                 0
23                 0
24                 0
25                 0
26                 0
27                 0
28                 0
29                 0
30                 0
31                 0
32                 0
33                 0
34                 0
35                 0
36                 0
37                 0
38                 0
39                 0
40                 0
41                 0
42                 0
43                 0
44                 0
45                 0
46                 0
47                 0
48                 0
49                 0
50                 0
51                 0
52                 0
53                 0
54                 0
55                 0
56                 0
57                 0
58                 0
59                 0
60                 0
61                 0
62                 0
63                 7
64                 0
65                 0
66                 0
67                 0
68                 0
69                 0
70                 0
71                 0
72                 0
73                 0
74                 0
75                 0
76                 0
77                 0
78                 0
79                 0
80                 0
81                 0
82                 0
83                 0
84                 0
85                 0
86                 0
87                 0
88                 0
89                 0
90                 0
91                 0
92                 0
93                 0
94                 0
95                 0
96                 0
97                 0
98                 0
99                 0
100                0
101                0
102                0
103                0
104                0
105                0
106                0
107                0
108                0
109                0
110                0
111                0
112                0
113                0
114                0
115                0
116                0
117                0
118                0
119                0
120                0
121                0
122                0
123                0
124                0
125                0
126                0
127                0
128                0
129                0
130                0
131                0
132                0
133                0
134                0
135                0
136                0
137                0
138                0
139                0
140                0
141                0
142                0
143                0