VB.net SQL数据透视表
我有两列需要按日期返回用户名计数VB.net SQL数据透视表,sql,sql-server,pivot,Sql,Sql Server,Pivot,我有两列需要按日期返回用户名计数 DateOnly Username 12/01/2014 00:00:00 Dave 12/01/2014 00:00:00 Bob 12/01/2014 00:00:00 Steve 12/01/2014 00:00:00 Richard 13/01/2014 00:00:00 Dave 13/01/2014 00:00:00 Dave 13/01/2014 00:00:00 B
DateOnly Username
12/01/2014 00:00:00 Dave
12/01/2014 00:00:00 Bob
12/01/2014 00:00:00 Steve
12/01/2014 00:00:00 Richard
13/01/2014 00:00:00 Dave
13/01/2014 00:00:00 Dave
13/01/2014 00:00:00 Bob
14/01/2014 00:00:00 Dave
以此类推,每天将始终有大约2000-3000条记录
我想把它展示得像
Username 12/01/2014 13/01/2014 14/01/2014
Dave 1 2 1
Bob 1 1 0
Steve 1 0 0
Richard 1 0 0
我希望用户选择两个日期进行搜索,即WHERE=12/01/2014和14/01/2014
所以我不知道会有多少列
有人能帮我解决这个问题吗?我的建议是,首先使用有限的日期编写查询,这样您就可以获得正确的PIVOT查询逻辑 如果值的数量有限,则可以轻松地对查询进行硬编码:
select username,
[2014-01-12], [2014-01-13], [2014-01-14]
from
(
select username, dateonly
from yourtable
where dateonly >= '2014-01-12'
and dateonly <= '2014-01-14'
) d
pivot
(
count(dateonly)
for dateonly in ([2014-01-12], [2014-01-13], [2014-01-14])
) piv;
然后,此表将用于创建动态列。此的动态SQL版本将是:
DECLARE @cols AS NVARCHAR(MAX),
@query AS NVARCHAR(MAX),
@startdate datetime,
@enddate datetime
DECLARE @ParmDefinition nvarchar(500)
SET @ParmDefinition = N'@startdt datetime, @enddt datetime'
-- these values would be passed into your stored procedure
set @startdate = '2014-01-10'
set @enddate = '2014-01-14'
-- this creates the list of final columns to be displayed using the
-- dates table. Using the calendar table makes sure that you return all dates you
-- requested even if you do not have those values in DateOnly
select @cols = STUFF((SELECT ',' + QUOTENAME(convert(varchar(10), dt, 120))
from dates
where dt >= @startdate
and dt <= @enddate
FOR XML PATH(''), TYPE
).value('.', 'NVARCHAR(MAX)')
,1,1,'')
set @query = 'SELECT username, ' + @cols + '
from
(
select username, dateonly
from yourtable
where dateonly >= @startdt
and dateonly <= @enddt
) x
pivot
(
count(dateonly)
for dateonly in (' + @cols + ')
) p '
execute sp_executesql @query,
@ParmDefinition,
@startdt = @startdate,
@enddt = @enddate;
DECLARE @cols AS NVARCHAR(MAX),
@query AS NVARCHAR(MAX),
@startdate datetime,
@enddate datetime
DECLARE @ParmDefinition nvarchar(500)
SET @ParmDefinition = N'@startdt datetime, @enddt datetime'
-- these values would be passed into your stored procedure
set @startdate = '2014-01-10'
set @enddate = '2014-01-14'
-- this creates the list of final columns to be displayed using the
-- dates table. Using the calendar table makes sure that you return all dates you
-- requested even if you do not have those values in DateOnly
select @cols = STUFF((SELECT ',' + QUOTENAME(convert(varchar(10), dt, 120))
from dates
where dt >= @startdate
and dt <= @enddate
FOR XML PATH(''), TYPE
).value('.', 'NVARCHAR(MAX)')
,1,1,'')
set @query = 'SELECT username, ' + @cols + '
from
(
select username, dateonly
from yourtable
where dateonly >= @startdt
and dateonly <= @enddt
) x
pivot
(
count(dateonly)
for dateonly in (' + @cols + ')
) p '
execute sp_executesql @query,
@ParmDefinition,
@startdt = @startdate,
@enddt = @enddate;
| USERNAME | 2014-01-10 | 2014-01-11 | 2014-01-12 | 2014-01-13 | 2014-01-14 |
|----------|------------|------------|------------|------------|------------|
| Bob | 0 | 0 | 1 | 1 | 0 |
| Dave | 0 | 0 | 1 | 2 | 1 |
| Richard | 0 | 0 | 1 | 0 | 0 |
| Steve | 0 | 0 | 1 | 0 | 0 |