可能重复:
How do I calculate a running total in SQL without using a cursor?
这有点难以解释,所以我会用一个例子展示我想要的东西:
假设我们有以下名为MonthProfit
的表:
[MonthId][Profit]
1, 10 -- January
2, 20 -- February
3, 30
4, 40
5, 50
6, 60
7, 70
8, 80
9, 90
10, 100
11, 110
12, 120 -- December
列profit
表示该月的利润。
但是,如果1月份有10个盈利,2月份有20个,2月份我们的总利润为30个。
所以我想创建一个显示以下内容的视图:
[MonthId][Profit][ProfitTotal]
1, 10, 10 -- January
2, 20, 30 -- February
3, 30, 60
4, 40, 100
5, 50, 150
6, 60, 210
7, 70, 280
8, 80, 360
9, 90, 450
10, 100, 550
11, 110, 660
12, 120, 780 -- December
我现在要解决的问题是这样的观点:
SELECT [MonthId]
,[Profit]
, (SELECT SUM([Profit])
FROM MonthProfit
WHERE [MonthId] <= outer.[MonthId]) as ProfitTotal
FROM MonthProfit as outer
然而,我认为这很慢,因为它必须一直重述所有内容,而且对我来说似乎并不优雅。有没有“好”的方法呢?
答案 0 :(得分:3)
我在这里尝试了一个小例子作为参考,根据要求生成结果
CREATE TABLE [dbo].[tbl_TotalPrevious](
[id] [int] IDENTITY(1,1) NOT NULL,
[name] [varchar](50) NOT NULL,
[values] [bigint] NOT NULL)
将数据插入表中
insert into tbl_TotalPrevious values ('A', 10)
insert into tbl_TotalPrevious values ('B', 20)
insert into tbl_TotalPrevious values ('C', 10)
insert into tbl_TotalPrevious values ('D', 10)
insert into tbl_TotalPrevious values ('E', 10)
insert into tbl_TotalPrevious values ('F', 10)
insert into tbl_TotalPrevious values ('G', 10)
insert into tbl_TotalPrevious values ('H', 10)
insert into tbl_TotalPrevious values ('I', 10)
insert into tbl_TotalPrevious values ('J', 10)
insert into tbl_TotalPrevious values ('K', 10)
insert into tbl_TotalPrevious values ('L', 10)
insert into tbl_TotalPrevious values ('M', 10)
insert into tbl_TotalPrevious values ('N', 10)
insert into tbl_TotalPrevious values ('O', 10)
insert into tbl_TotalPrevious values ('P', 10)
insert into tbl_TotalPrevious values ('Q', 10)
insert into tbl_TotalPrevious values ('R', 10)
insert into tbl_TotalPrevious values ('S', 10)
insert into tbl_TotalPrevious values ('T', 10)
insert into tbl_TotalPrevious values ('U', 10)
insert into tbl_TotalPrevious values ('V', 10)
insert into tbl_TotalPrevious values ('W', 10)
insert into tbl_TotalPrevious values ('X', 10)
insert into tbl_TotalPrevious values ('Y', 10)
创建一个函数,例如。
ALTER FUNCTION testtotal
(
@id int
)
RETURNS int
AS
BEGIN
DECLARE @Result int
SELECT @Result = (SELECT SUM([values])
FROM tbl_TotalPrevious
WHERE [id] <= @id)
RETURN @Result
END
GO
单个查询生成的结果
SELECT [id],[values], (dbo.testtotal(id)) as TotalVals FROM tbl_TotalPrevious
希望上面的问题能够解决您的时间问题并根据需要更快地生成数据。
答案 1 :(得分:0)
尝试下面这样的事情,乍一看看很好: - )。
create table #tab ([MonthId] int, [Profit] int)
insert into #tab select 1, 10 -- January
insert into #tab select 2, 20 -- February
insert into #tab select 3, 30
insert into #tab select 4, 40
insert into #tab select 5, 50
insert into #tab select 6, 60
insert into #tab select 7, 70
insert into #tab select 8, 80
insert into #tab select 9, 90
insert into #tab select 10, 100
insert into #tab select 11, 110
insert into #tab select 12, 120 -- December
select t.*, t3.total
from #tab t
join (
select t1.monthId,
sum(t2.profit) as total
from #tab t1
join #tab t2 on t1.monthId >= t2.monthId
group by t1.monthId
) t3 on t.monthId = t3.monthId
答案 2 :(得分:0)
declare @MonthProfit table
(
[MonthId] int,
[Profit] int
)
insert into @MonthProfit values
(1, 10),(2, 20),(3, 30),(4, 40),
(5, 50),(6, 60),(7, 70),(8, 80),
(9, 90),(10, 100),(11, 110),(12, 120)
;with C as
(
select M.MonthId,
M.Profit
from @MonthProfit as M
where M.MonthId = 1
union all
select M.MonthId,
C.Profit + M.Profit
from @MonthProfit as M
inner join C
on M.MonthId = C.MonthId + 1
)
select C.MonthId,
C.Profit
from C
order by C.MonthId
答案 3 :(得分:-1)
这似乎是一个不太优雅的选择,但它运作正常。
如果你想改进,你有几个选择: