我正在使用SQL Server在两行中交换两个值。让我说明一下:
[ord] [name]
1 John
4 Jack
7 Pete
9 Steve
11 Mary
说,我需要为“Pete”和“Steve”交换[ord]数字,以使这个表格如此:
[ord] [name]
1 John
4 Jack
9 Pete
7 Steve
11 Mary
这似乎是一项微不足道的任务,但我似乎无法为它编写SQL UPDATE语句。
答案 0 :(得分:19)
如果'Peter'
和'Steve'
在您的表格中是唯一的,则可以执行以下操作:
UPDATE TableX
SET ord = ( SELECT MIN(ord) + MAX(ord)
FROM TableX
WHERE name IN ('Peter', 'Steve')
) - ord
WHERE name IN ('Peter', 'Steve')
或(由@Erwin改进):
UPDATE TableX
SET ord = ( SELECT SUM(ord)
FROM TableX
WHERE name IN ('Peter', 'Steve')
) - ord
WHERE name IN ('Peter', 'Steve')
答案 1 :(得分:7)
这与您之前的问题非常相似:SQL to move rows up or down in two-table arrangement
我为你准备了另一个demo on data.stackexchange.com。
编辑:现在简化了设置,因此我相应地简化了查询。
WITH x AS (SELECT name, ord FROM t WHERE name = 'Pete') -- must be unique!
, y AS (SELECT name, ord FROM t WHERE name = 'Steve') -- must be unique!
UPDATE t
SET ord = z.ord
FROM (
SELECT x.name, y.ord FROM x,y
UNION ALL
SELECT y.name, x.ord FROM x,y
) z
WHERE t.name = z.name;
此查询仅在可以找到这两行时更新,否则不执行任何操作。
答案 2 :(得分:6)
使用CASE表达式:
UPDATE yourtable
SET [ord] = CASE [ord] WHEN 9 THEN 7
WHEN 7 THEN 9 END
WHERE [ord] IN (7, 9)
答案 3 :(得分:3)
UPDATE Table_1
SET ord =
CASE name
WHEN 'Pete' THEN (SELECT ord FROM Table_1 WHERE name = 'Steve')
WHEN 'Steve' THEN (SELECT ord FROM Table_1 WHERE name = 'Pete')
END
WHERE name IN ('Pete', 'Steve')
您可以轻松地将'Pete'和'Steve'替换为其他名称......
答案 4 :(得分:0)
BEGIN TRANSACTION
UPDATE TABLENAME
SET ord = 9
where name = 'Pete'
UPDATE TABLENAME
SET ord = 7
where name = 'Steve'
COMMIT TRANSACTION
答案 5 :(得分:0)
使用以下脚本交换值
IF OBJECT_ID('tempdb..#TempTable') IS NOT NULL DROP TABLE #TempTable
CREATE TABLE #TempTable
(
ROW_ID INT IDENTITY(1,1),
SEQUENCE_NO INT,
ID INT
)
DECLARE @Id INT = 24780, --Row Id
DECLARE @NewPosition INT = -1; -- (Move Up or Move Down +1 for Up and -1 For Down)
DECLARE @SEQUENCE_NO INT = 0;
INSERT INTO #TempTable
SELECT SEQUENCE_NO ,ID
FROM TABLE_NAME S
WHERE ID = @Id
SET @SEQUENCE_NO = (SELECT SEQUENCE_NO FROM #TempTable)
INSERT INTO #TempTable
SELECT SEQUENCE_NO AS SNO,ID
FROM TABLE_NAME S
WHERE ID <> @Id
AND SEQUENCE_NO = (@SEQUENCE_NO + @NewPosition) -- (Move Up or Move Down +1 for Up and -1 For Down)
--Add check point here temp table to have 2 exact records
;WITH x AS (SELECT ID, SEQUENCE_NO FROM #TempTable WHERE ROW_ID = 1)
, y AS (SELECT ID, SEQUENCE_NO FROM #TempTable WHERE ROW_ID = 2)
UPDATE #TempTable
SET SEQUENCE_NO = z.SEQUENCE_NO
FROM (
SELECT x.ID, y.SEQUENCE_NO FROM x,y
UNION ALL
SELECT y.ID, x.SEQUENCE_NO FROM x,y
) z
WHERE #TempTable.ID = z.ID;
UPDATE SI
SET SI.SEQUENCE_NO = T.SEQUENCE_NO -- (Swap Values here)
FROM TABLE_NAME SI
JOIN #TempTable T ON SI.ID = T.ID