2013-05-30 81 views
43

我想執行更新和選擇...基本上,基於索引更新,然後選擇已更新的行ID。更新輸出到一個變量

這是一個簡單的使用OUTPUT子句:

UPDATE Foo 
SET Bar = 1 
OUTPUT INSERTED.Id 
WHERE Baz = 2 

但現在,我怎麼到這個變量?

DECLARE @id INT 

這三個不起作用:

UPDATE Foo 
SET Bar = 1 
OUTPUT @id = INSERTED.Id 
WHERE Baz = 2 

SET @id = 
(UPDATE Foo 
SET Bar = 1 
OUTPUT INSERTED.Id 
WHERE Baz = 2) 

SET @id = 
(SELECT Id FROM (UPDATE Foo 
       SET Bar = 1 
       OUTPUT INSERTED.Id Id 
       WHERE Baz = 2) z) 

這包括最後一個,因爲它讓我暫時興奮,當所有的紅色squigglies Management Studio中走了。唉,我得到這個錯誤:

A nested INSERT, UPDATE, DELETE, or MERGE statement is not allowed in a SELECT statement that is not the immediate source of rows for an INSERT statement. 

回答

44

如果只有一行受到影響,那麼可以在沒有表變量的情況下完成。

DECLARE @id INT 

UPDATE Foo 
SET Bar = 1, @id = id 
WHERE Baz = 2 

SELECT @id 
+1

我從來沒有想到這一點。非常好! –

+1

感謝科裏,我想知道更新內的set關鍵字是否能夠設置一個變量,它的工作原理! –

+0

這將工作與'插入'爲單個受影響的行? – rahoolm

62

因爲更新會影響多行,它需要一個表來存儲它的結果:如果你確定只有一排將受到影響

declare @ids table (id int); 

UPDATE Foo 
SET Bar = 1 
OUTPUT INSERTED.Id INTO @ids 
WHERE Baz = 2 

,你可以把這個ID拉出來:

declare @id int 
select top 1 @id = id 
from @ids 
1

另外,如果只有一個行受到影響:

DECLARE @id INT 

UPDATE Foo 
SET @id = Bar = 1 ---Yes, this is valid! 
WHERE Baz = 2 

SELECT @id