我有这样的数据:
Date Count1 Count2 Count3 ... Countxx
01-05-2012 1 0 1 2
01-05-2012 2 1 3 0
01-05-2012 2 3 3 1
02-05-2012 1 3 2 0
02-05-2012 5 2 0 0
我需要计算按日期分组的各个字段(Count1到Countxx)的总和并写下这个SQL:
select sum(count1), sum(count2), sum(count3), .. , sum(countxx)
from table1 group by date
我的第一个问题:SQL服务器中是否有任何方法可以自动执行此操作(不知道字段数,因为每次字段的名称和数量都会不同,因此手动编写SQL非常麻烦)。 / p>
其次,如何计算当前行减去前一行的值和前7行的平均值?
谢谢!
答案 0 :(得分:2)
create procedure USP_FindSum @tablename varchar(100)
as
begin
create table #temp(id int identity(1,1),name varchar(100))
declare @sqlcmd nvarchar(max)=''
SET @sqlcmd= N'Insert into #temp select name from sys.columns col_table where
col_table.object_id=object_id('''+@tablename+''')'
EXEC sp_executesql @sqlcmd
declare @sqlseg varchar(max)=''
declare @tempcount int
declare @i int=1
select @tempcount=COUNT(id) from #temp
while(@i<=@tempcount)
BEGIN
declare @CName varchar(100)
SELECT @CName= name from #temp where id=@i
if(@i!=@tempcount)
SET @sqlseg=+@sqlseg+'sum('+@CName+')'+','
else
SET @sqlseg =+@sqlseg+'sum('+@CName+')'
SET @i=@i+1
END
SET @sqlcmd=N'select '+@sqlseg+' from '+@tablename
EXEC sp_executesql @sqlcmd
DROP TABLE #temp
END
假设表中的所有列都是可求和的。由于您的要求很奇怪,这种解决方法也可能如此。
只需将表名作为参数传递并执行,
Exec USP_FindSum '<tablename here>'
答案 1 :(得分:0)
无法对列的变量列表求和,您必须全部指定。
查找上一行的一种方法是outer apply
,例如:
select Date
, cur.count1 - isnull(prev.count1,0) as Delta1
from Table1 cur
outer apply
(
select top 1 *
from Table1 prev
where prev.Date < cur.Date
order by
prev.Date desc
) prev
另一种方法是根据row_number()
加入表:
; with t1 as
(
select row_number() over (order by Date) as rn
, *
from Table1
)
select Date,
, cur.count1 - isnull(prev.count1,0) as Delta
from t1 cur
left join
t1 prev
on cur.rn = prev.rn + 1