如何交换连续2列的值? SQL Server

时间:2014-03-12 09:32:47

标签: sql sql-server

我的表名为Info,其中包含ID, tName, restNameisOpen列。

我有这样的价值观,例如:

ID (Unique) | tName |  restName | isOpen
-----------------------------------------    
 9          - TN10  -    RN10   -   0
10          - TN10  -    RN10   -   1
11          - TN11  -    RN11   -   1

我想将tNamerestName值换成isOpen=1

ID (Unique) | tName |  restName | isOpen
----------------------------------------    
 9          - TN10  -    RN10   -   0
10          - TN11  -    RN11   -   1
11          - TN10  -    RN10   -   1

我知道在查询之前我应该​​更改的值,我的意思是我知道tName-restName应该更改为tName-restName

我对查询很新,我无法弄清楚如何交换值。如果它是像C这样的语言,我只会使用临时值并交换它们。它可以用1个查询完成吗?我看到交换列时很容易,但我找不到任何有用的材料。

更新

我忘了告诉我当时我不知道ID的值,也不想用另一个查询来获取它们。

如果有可能,我想进行“将值restName=RN10tName=TN10restName=RN11以及tName=TN11isOpen=1交换”的查询。所以选择大概是tNamerestNameisOpen我猜。

感谢您的回复,

度过愉快的一天

3 个答案:

答案 0 :(得分:2)

对于更通用的交换,我们说我们有:

declare @Swaps table (
    tFirst varchar(10) not null,
    rFirst varchar(10) not null,
    tSecond varchar(10) not null,
    rSecond varchar(10) not null
)
INSERT INTO @Swaps (tFirst,rFirst,tSecond,rSecond) VALUES
                   ('TN10','RN10','TN11','RN11')
                 --And more rows
UPDATE i
SET tName = o.tName,
    restName = o.restName
FROM @Swaps s
    inner join
     Info i
        on
           ((s.tFirst = i.tName and s.rFirst = i.restName) or
            (s.tSecond = i.tName and s.rSecond = i.restName)) and
           i.IsOpen = 1
    inner join
     Info o
        on
           ((s.tFirst = o.tName and s.rFirst = o.restName) or
            (s.tSecond = o.tName and s.rSecond = o.restName)) and
           o.IsOpen = 1 and
           (i.tName <> o.tName or i.restName <> o.restName)

早期回答

对于此特定交换,可以按以下方式完成:

UPDATE i
SET tName = o.tName
    restName = o.restName
FROM Info i
INNER JOIN Info o
on (
  (i.ID = 10 and o.ID = 11) or
  (i.ID = 11 and o.ID = 10)
)

但我不确定您的实际问题规模有多大。如果存在大量交换,您可能希望将所有这些组合存储在另一个(临时)表中,并进行进一步的连接。

答案 1 :(得分:0)

我经过长时间尝试后写了一个查询:)我完全按照自己的意愿行事,但我无法确定它是否完全正确。如果有人能检查并告诉我,我会很高兴。谢谢......

UPDATE Info 
SET tName = CASE tName 
WHEN @tNameOld THEN @tNameNew
WHEN @tNameNew THEN @tNameOld
END,     
restName = CASE restName 
WHEN @restNameOld THEN @restNameNew
WHEN @restNameNew THEN @restNameOld 
END     
WHERE tName in (@tNameOld,@tNameNew)     
AND isOpen=1     
AND restName in (@restNameOld,@restNameNew)

答案 2 :(得分:0)

试试这个:

<强>设置

CREATE TABLE #Info
(
    ID INT Primary Key NOT NULL,
    tName Varchar(50) NOT NULL,
    restName VARCHAR(50)NOT NULL,
    isOpen bit NOT NULL

)

INSERT INTO #Info   VALUES 
          ( 9, 'TN10', 'RN10', 0),
    (10, 'TN10','RN10', 1),
    (11, 'TN11','RN11', 1)

select *
from #Info


UPDATE #info
    SET tName = newTName,
        restName = newRestName
FROM #info i
INNER JOIN 
    (
        select id, tName newRestName, restName newTName  
        from #Info
        WHERE isOpen = 1
    ) i2
ON i.ID = i2.ID

SELECT *
FROM #Info