【问题标题】:sql update query on temporary table临时表上的sql更新查询
【发布时间】:2017-11-26 22:57:25
【问题描述】:

我有一个像下面这样的临时表:

  Date    Fund  NotAdded    Dividend
1/1/2017    A     0           0
1/2/2017    A     0           0
1/3/2017    A   100           0
1/4/2017    A     0         200
1/5/2017    A    50          50
1/1/2017    B     0           0
1/2/2017    B   100           0
1/3/2017    B     0         200
1/4/2017    B     0           0

我想对上表运行更新查询,结果如下:

Date      Fund  NotAdded    Dividend   Notional
1/1/2017    A     0           0         5000 (this value is known)
1/2/2017    A     0           0         5000
1/3/2017    A   100           0         5100
1/4/2017    A     0         200         5300
1/5/2017    A    50          50         5400
1/1/2017    B     0           0         2000
1/2/2017    B   100           0         2100  
1/3/2017    B     0         200         2300
1/4/2017    B     0           0         2300

对于每个基金,默认名义价值是已知的。即在上面的示例中,基金 A 为 5000,基金 B 为 2000。

我尝试了但无法获得所需的输出。任何帮助!!!

【问题讨论】:

  • “(这个值是已知的)”是什么意思?它似乎是凭空发明的。
  • 这个新专栏是从哪里来的?添加新列是预期的结果吗?
  • @GordonLinoff 该值来自另一个查询结果。您现在可以将其作为示例。 :)
  • @Hybris95 是的,它应该在预期的结果中。
  • 你能添加查询来恢复每行的 Notional 值还是我们必须猜测它?

标签: sql sql-server sql-server-2008 insert-update


【解决方案1】:

您似乎想要NotAddedDividend 的累积总和加上一些随机数。后者我无能为力。

在 SQL Server 2012+ 中,您将使用累积和函数。在 SQL Server 2008 中,您可以使用稍后的联接 (apply) 或相关子查询:

select t.*,
       (select sum(t2.NotAdded) + sum(t2.Dividend)
        from #temp t2
        where t2.fund = t.fund and
              t2.date <= t.date
       ) as Cumulative
from #temp t;

您可以将“已知”值添加到累积中以获得最终值。

如果您想将此作为更新:

update t
    set notional = notional + 
                   (select sum(t2.NotAdded) + sum(t2.Dividend)
                    from #temp t2
                    where t2.fund = t.fund and
                          t2.date <= t.date
                   )
    from #temp t;

这假定notional 以相关值开头。

【讨论】:

    【解决方案2】:

    考虑到前面的行值,您可以使用带有LAG 函数的COMPUTED 列来SUM 您的列..

    只需OVER 对您的基金和日期列。 首选使用主键,但如果你没有主键,我想它现在可以完成这项工作。

    【讨论】:

      【解决方案3】:

      假设这是一次性问题,而不是永久性问题。我根据以下链接提出了以下解决方案:

      How to get cumulative sum

      我将简要解释一下我所做的事情,然后您可以查看下面的代码。

      首先我创建了一个临时表来模仿你的临时表,我插入了一个标识(1,1)。这是计算部分所必需的。

      然后,我在第一行的基金类型 a (5000) 和第一个基金类型 b (2000) 中插入了您所拥有的数据以及“已知值”。

      然后在临时表中进行两次插入,其中第一个主表连接到自身并将其 NotAdded + Dividend + Notional 值从第二个较高的 id(身份字段)添加到较低的 id。

      之后,剩下要做的就是更新与 id 匹配的原始表。请看下面的代码。

      --create temp table
      DECLARE @TEMP TABLE 
      (
          [id] INT IDENTITY(1,1), 
          [DATE] [datetime] NULL,
          [Fund] [varchar](1) NULL,
          [NotAdded] [int] NULL,
          [Dividend] [int] NULL,
          [Notional] [int] NULL   
      )
      
      
      --insert into temp table with first known value
      INSERT INTO @TEMP ([DATE], [Fund], [NotAdded], [Dividend], Notional)
      VALUES  ('1/1/2017','A',0,0,5000), --First value of A is known
              ('1/2/2017','A',0,0,0),
              ('1/3/2017','A',100,0,0),
              ('1/4/2017','A',0,200,0),
              ('1/5/2017','A',50,50,0),
              ('1/1/2017','B',0,0,2000), --First value of B is known
              ('1/2/2017','B',100,0,0),
              ('1/3/2017','B',0,200,0),
              ('1/4/2017','B',0,0,0)
      
      --select into temp table for type a so that we can update the @temp table later 
      SELECT T.id, T.Fund, T.NotAdded, T.Dividend, SUM(T2.NotAdded + T2.Dividend + T2.Notional)  AS Notional_Sum
      INTO #TEMP_A
      FROM @TEMP T 
          INNER JOIN @TEMP t2 on T.id >= t2.id
                              AND T2.Fund = T.Fund
      WHERE 1=1
          AND T.Fund = 'A'
      GROUP BY T.id, T.Fund,T.NotAdded, T.Dividend
      ORDER BY T.id
      
      --select into temp table for type b so that we can update the @temp table later 
      SELECT T.id, T.Fund, T.NotAdded, T.Dividend, SUM(T2.NotAdded + T2.Dividend + T2.Notional)  AS Notional_Sum
      INTO #TEMP_B
      FROM @TEMP T 
          INNER JOIN @TEMP t2 on T.id >= t2.id
                              AND T2.Fund = T.Fund
      WHERE 1=1
          AND T.Fund = 'B'
      GROUP BY T.id, T.Fund,T.NotAdded, T.Dividend
      ORDER BY T.id
      
      --finally do updates
      UPDATE T
      SET T.Notional = TTS.Notional_Sum
      FROM @TEMP T
              INNER JOIN #TEMP_A TTS ON TTS.id = T.id
      WHERE 1=1
      
      UPDATE T
      SET T.Notional = TTS.Notional_Sum
      FROM @TEMP T
              INNER JOIN #TEMP_B TTS ON TTS.id = T.id
      WHERE 1=1
      
      
      --select to view
      SELECT  * FROM @TEMP
      
      --drop temp tables
      DROP TABLE #TEMP_A, #TEMP_B
      

      【讨论】:

        猜你喜欢
        • 2013-03-26
        • 1970-01-01
        • 2013-08-09
        • 2015-09-05
        • 2023-01-20
        • 1970-01-01
        • 2022-10-18
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多