在SQL Server中,可以使用insert将行插入到表中。。SELECT语句:
INSERT INTO Table (col1, col2, col3)
SELECT col1, col2, col3
FROM other_table
WHERE sql = 'cool'
是否也可以使用SELECT更新表?我有一个包含这些值的临时表,并希望使用这些值更新另一个表。也许是这样的:
UPDATE Table SET col1, col2
SELECT col1, col2
FROM other_table
WHERE sql = 'cool'
WHERE Table.id = other_table.id
另一种尚未提及的可能性是将SELECT语句本身放入CTE,然后更新CTE。
WITH CTE
AS (SELECT T1.Col1,
T2.Col1 AS _Col1,
T1.Col2,
T2.Col2 AS _Col2
FROM T1
JOIN T2
ON T1.id = T2.id
/*Where clause added to exclude rows that are the same in both tables
Handles NULL values correctly*/
WHERE EXISTS(SELECT T1.Col1,
T1.Col2
EXCEPT
SELECT T2.Col1,
T2.Col2))
UPDATE CTE
SET Col1 = _Col1,
Col2 = _Col2;
这样做的好处是,首先很容易单独运行SELECT语句来检查结果的完整性,但如果源表和目标表中的列名称相同,则需要如上所述对列进行别名。
这也具有与专有UPDATE相同的限制。。。其他四个答案中显示了FROM语法。如果源表位于一对多连接的多方,则无法确定更新中将使用哪些可能匹配的连接记录(如果多次尝试更新同一行,MERGE会通过引发错误来避免此问题)。
另一种尚未提及的可能性是将SELECT语句本身放入CTE,然后更新CTE。
WITH CTE
AS (SELECT T1.Col1,
T2.Col1 AS _Col1,
T1.Col2,
T2.Col2 AS _Col2
FROM T1
JOIN T2
ON T1.id = T2.id
/*Where clause added to exclude rows that are the same in both tables
Handles NULL values correctly*/
WHERE EXISTS(SELECT T1.Col1,
T1.Col2
EXCEPT
SELECT T2.Col1,
T2.Col2))
UPDATE CTE
SET Col1 = _Col1,
Col2 = _Col2;
这样做的好处是,首先很容易单独运行SELECT语句来检查结果的完整性,但如果源表和目标表中的列名称相同,则需要如上所述对列进行别名。
这也具有与专有UPDATE相同的限制。。。其他四个答案中显示了FROM语法。如果源表位于一对多连接的多方,则无法确定更新中将使用哪些可能匹配的连接记录(如果多次尝试更新同一行,MERGE会通过引发错误来避免此问题)。
Use:
drop table uno
drop table dos
create table uno
(
uid int,
col1 char(1),
col2 char(2)
)
create table dos
(
did int,
col1 char(1),
col2 char(2),
[sql] char(4)
)
insert into uno(uid) values (1)
insert into uno(uid) values (2)
insert into dos values (1,'a','b',null)
insert into dos values (2,'c','d','cool')
select * from uno
select * from dos
或者:
update uno set col1 = (select col1 from dos where uid = did and [sql]='cool'),
col2 = (select col2 from dos where uid = did and [sql]='cool')
OR:
update uno set col1=d.col1,col2=d.col2 from uno
inner join dos d on uid=did where [sql]='cool'
select * from uno
select * from dos
如果两个表中的ID列名相同,则只需将表名放在要更新的表之前,并为所选表使用别名,即:
update uno set col1 = (select col1 from dos d where uno.[id] = d.[id] and [sql]='cool'),
col2 = (select col2 from dos d where uno.[id] = d.[id] and [sql]='cool')
整合所有不同的方法。
选择更新使用公共表表达式更新合并
示例表结构如下,将从Product_BAK更新为Product表。
表产品
CREATE TABLE [dbo].[Product](
[Id] [int] IDENTITY(1, 1) NOT NULL,
[Name] [nvarchar](100) NOT NULL,
[Description] [nvarchar](100) NULL
) ON [PRIMARY]
表产品_BAK
CREATE TABLE [dbo].[Product_BAK](
[Id] [int] IDENTITY(1, 1) NOT NULL,
[Name] [nvarchar](100) NOT NULL,
[Description] [nvarchar](100) NULL
) ON [PRIMARY]
1.选择更新
update P1
set Name = P2.Name
from Product P1
inner join Product_Bak P2 on p1.id = P2.id
where p1.id = 2
2.使用公共表表达式更新
; With CTE as
(
select id, name from Product_Bak where id = 2
)
update P
set Name = P2.name
from product P inner join CTE P2 on P.id = P2.id
where P2.id = 2
3.合并
Merge into product P1
using Product_Bak P2 on P1.id = P2.id
when matched then
update set p1.[description] = p2.[description], p1.name = P2.Name;
在这个Merge语句中,如果在目标中找不到匹配的记录,但在源中存在,我们可以插入,请查找语法:
Merge into product P1
using Product_Bak P2 on P1.id = P2.id;
when matched then
update set p1.[description] = p2.[description], p1.name = P2.Name;
WHEN NOT MATCHED THEN
insert (name, description)
values(p2.name, P2.description);