如何使用NTILE函数更新表中的值?

时间:2017-02-22 17:21:25

标签: sql-server tsql

摘要:我试图将这些股票因素按最高分位和最低分位排列,以构建多头/空头组合。

表:

enter image description here

期望的结果:

enter image description here

使用的代码:

UPDATE MOMENTUM_Quintile 
SET [2006-12-30] = NTILE(5) OVER (ORDER BY [2006-12-30] DESC)
FROM MOMENTUM_Quintile

错误讯息:

  

Msg 4108,Level 15,State 1,Line 7
  窗口函数只能出现在SELECT或ORDER BY子句中。

3 个答案:

答案 0 :(得分:3)

错误很清楚,为什么你不能这样做,与逻辑查询处理有关。你可以尝试下面的

 With cte
 as(
 select *, NTILE(5) OVER (order by [2006-12-30] desc) as ntile
from
MOMENTUM_Quintile
)
update cte 
set [2006-12-30]=ntile

答案 1 :(得分:1)

您需要将该函数放在子查询中:

UPDATE t 
SET [2006-12-30] = [2006-12-30_New]
FROM (  SELECT  [2006-12-30],
                [2006-12-30_New]= NTILE(5) OVER (ORDER BY [2006-12-30] DESC)
        FROM    MOMENTUM_Quintile
    ) AS t;

对于它的价值,将日期作为列名称有点代码味道。我怀疑你需要规范化你的数据。此外,在进行此类更新时,您将丢失原始数据。因此,虽然上述方法有效,但我认为您可能需要重新考虑这一点。

答案 2 :(得分:0)

您可以使用可更新的CTE执行此操作:

with toupdate as (
      select mq.*, NTILE(5) OVER (ORDER BY [2006-12-30] DESC) as tile
      from MOMENTUM_Quintile mq
     )
update toupdate
    set [2006-12-30] = tile;

您可以为多列重复此操作:

with toupdate as (
      select mq.*,
             NTILE(5) OVER (ORDER BY [2006-12-30] DESC) as tile1,
             NTILE(5) OVER (ORDER BY [2007-01-30] DESC) as tile2
      from MOMENTUM_Quintile mq
     )
update toupdate
    set [2006-12-30] = tile1,
        [2007-01-30] = tile2;