使用同一 table 中的一组数据更新 table 中的行

Updating rows in table with group of data from the same table

我下面有这个table:

Indicator  Year         Month     FirstDayPeriod      NrOfThings   NmbrOfThingsPastYear
99         2013         1         Jan  1 2013         10858         
99         2013         2         Feb  1 2013         8264         
99         2013         3         Mar  1 2013         9716         
99         2013         4         Apr  1 2013         8549         
99         2013         5         May  1 2013         8144         
99         2013         6         Jun  1 2013         7917         
99         2013         7         Jul  1 2013         9585         
99         2013         8         Aug  1 2013         7426         
99         2013         9         Sep  1 2013         7877         
99         2013         10        Oct  1 2013         9707         
99         2013         11        Nov  1 2013         8925         
99         2013         12        Dec  1 2013         13709         
99         2014         1         Jan  1 2014         11183         
99         2014         2         Feb  1 2014         8518         
99         2014         3         Mar  1 2014         10545         
99         2014         4         Apr  1 2014         9582         
99         2014         5         May  1 2014         10278         
99         2014         6         Jun  1 2014         9330         
99         2014         7         Jul  1 2014         11366         
99         2014         8         Aug  1 2014         9161         
99         2014         9         Sep  1 2014         10651         
99         2014         10        Oct  1 2014         11331         
99         2014         11        Nov  1 2014         10624         126278
99         2014         12        Dec  1 2014         17958         130527
99         2015         1         Jan  1 2015         11431         130775

最后一列 (NmbrOfThingsPastYear) 是过去 12 个月 NrOfThings 的总数。因此,2014 年 11 月的 NmbrOfThingsPastYear 由 2014 年 11 月、2014 年 10 月、2014 年 9 月等的 NrOfThings 的总和定义...直到 2013 年 12 月... 我想做的是用 table...

中的值更新 table 中的列 NmbrOfThingsPastYear

此声明提供了 2014 年 11 月的正确值:

SELECT 
Indicator,
MAX(tsum.FirstDayPeriod),
SUM(tsum.AantalTaken)
FROM tempdb..TableAbove tsum 
WHERE tsum.FirstDayPeriod > dateadd(mm, -12, '20141101') 
  AND tsum.FirstDayPeriod <= '20141101'
GROUP BY 
Indicator

所以我正在寻找一种结构,我可以在其中使用值更新 table 中每一行的 NmbrOfThingsPastYear 列(前面 NrOfThings 的总和12个月)每个月..

有人可以帮助我吗? 提前致谢!

我已经实现了你想要的,但是使用了游标。如果有人转换这个或 post 基于集合的逻辑,那么就用那个。

我创建了一个名为 #stuff 的临时文件 table 以复制您正在尝试执行的操作。如您所见,每个 FirstDayPeriod 日期都是循环的,然后对前 12 个月的 NrOfThings 求和。然后根据 FirstDayPeriod 更新 NrOfthingsPastYear。您可以在此处轻松地增加指标等内容的范围,但下面应该为您提供一个基础:

IF OBJECT_ID('tempdb..#Stuff') IS NOT NULL DROP TABLE #Stuff

GO

CREATE TABLE #Stuff
(Indicator int, 
FirstDayPeriod datetime,
NrOfthings int,
NrOfthingspastyear int)

INSERT INTO #Stuff ( Indicator, FirstDayPeriod, NrOfthings, NrOfThingsPastYear)

VALUES (99, 'Jan 1 2013', '32432', 0),
 (99, 'Feb 1 2013', '322', 0),
 (99, 'Mar 1 2013', '312', 0),
 (99, 'Apr 1 2013', '32432', 0),
 (99, 'May 1 2013', '32', 0),
 (99, 'Jun 1 2013', '32432', 0),
 (99, 'Jul 1 2013', '32432', 0),
 (99, 'Aug 1 2013', '32092', 0),
 (99, 'Sep 1 2013', '2', 0),
 (99, 'Oct 1 2013', '32432', 0),
 (99, 'Nov 1 2013', '32432', 0),
 (99, 'Dec 1 2013', '312', 0),
 (99, 'Jan 1 2014', '32232', 0),
 (99, 'Feb 1 2014', '32432', 0),
 (99, 'Mar 1 2014', '32432', 0),
 (99, 'Apr 1 2014', '3932', 0),
 (99, 'May 1 2014', '3242', 0),
 (99, 'Jun 1 2014', '32432', 0),
 (99, 'Jul 1 2014', '324', 0),
 (99, 'Aug 1 2014', '32432', 0),
 (99, 'Sep 1 2014', '3532', 0),
 (99, 'Oct 1 2014', '32432', 0),
 (99, 'Nov 1 2014', '332', 0),
 (99, 'Dec 1 2014', '3232', 0)


DECLARE @FirstDayPeriod datetime

DECLARE crs1 CURSOR 

FOR

SELECT
    FirstDayPeriod
FROM #Stuff

OPEN crs1
FETCH NEXT FROM Crs1 Into @FirstDayPeriod

WHILE @@FETCH_STATUS = 0

BEGIN

    UPDATE 
        #Stuff
    SET
        NrOfThingsPastYear =( 
                            SELECT
                                SUM(nrOfThings)
                            FROM
                                #Stuff
                            WHERE FirstDayPeriod > dateadd(mm, -12, @FirstDayPeriod) 
                              AND FirstDayPeriod <= @FirstDayPeriod
                            )
    WHERE
        FirstDayPeriod = @FirstDayPeriod

FETCH NEXT FROM crs1 INTO @FirstDayPeriod

END

CLOSE crs1
DEALLOCATE crs1

SELECT * FROM #Stuff

只是加入和分组的问题。查询应该是相对不言自明的。只需获取 table 的每一行,然后将其与之前的 11 个月连接起来。然后对该行的日期进行分组(应该有 12 个)并添加连接值。

SELECT  tsum1.Indicator, tsum1.FirstDayPeriod, 
        Sum( tsum2.NrOfThings ) NmbrOfThingsPastYear
FROM    TableAbove tsum1
join    TableAbove tsum2
    on  tsum2.Indicator = tsum1.Indicator
    and tsum2.FirstDayPeriod -- between now and a year ago
        between DateAdd( Month, -11, tsum1.FirstDayPeriod )
            and tsum1.FirstDayPeriod
group BY tsum1.Indicator, tsum1.FirstDayPeriod -- gather into 12-month chunks
having count(*) > 11 -- leave out any chunks of less than 12 months
order by tsum1.Indicator, tsum1.FirstDayPeriod;

having 子句可防止出现部分结果,但您可以根据需要省略它。

将其转换为 update 语句会因为分组而有点棘手。如果不出意外,只需将此结果集反馈到与 table 的连接中并使用它。

这里是Fiddle。它使用 SQL 服务器,因为 SQLFiddle 没有 Sybase,但它会关闭。

我想我应该在家里安装 Sybase...