如何插入多条记录并获取标识值?

时间:2008-09-18 19:24:12

标签: sql sql-server sql-server-2005

我正在从另一个表B中将多个记录插入到表A中。是否有办法获取表A记录的标识值并更新表b记录而不执行游标?

Create Table A
(id int identity,
Fname nvarchar(50),
Lname nvarchar(50))

Create Table B
(Fname nvarchar(50),
Lname nvarchar(50),
NewId int)

Insert into A(fname, lname)
SELECT fname, lname
FROM B

我正在使用MS SQL Server 2005。

8 个答案:

答案 0 :(得分:144)

使用2005年的输出子句:

DECLARE @output TABLE (id int)

Insert into A (fname, lname)
OUTPUT inserted.ID INTO @output
SELECT fname, lname FROM B

select * from @output

现在你的表变量具有你插入的所有行的标识值。

答案 1 :(得分:5)

仔细阅读您的问题,您只想根据表A中的新身份值更新表B.

插入完成后,只需运行更新...

UPDATE B
SET NewID = A.ID
FROM B INNER JOIN A
     ON (B.FName = A.Fname AND B.LName = A.LName)

这假设FName / LName组合可用于键匹配表之间的记录。如果不是这种情况,您可能需要添加额外的字段以确保记录正确匹配。

如果您没有允许您匹配记录的备用密钥,那么根本没有意义,因为表B中的记录无法彼此区分。

答案 2 :(得分:0)

如果您总是想要这种行为,可以在TableA上放置一个AFTER INSERT触发器来更新表B.

答案 3 :(得分:0)

您可以加入row number。这是可能的,因为它是一个标识,它只会在您添加项目时递增,这将按您选择它们​​的顺序。

答案 4 :(得分:0)

据我所知,您遇到的问题是您想要插入具有标识列的表A,并且您希望保留表B中没有的标识。

为了做到这一点,你只需要打开表A上的身份插入。这将允许你在插入时定义你的ID,只要它们没有冲突,你应该没问题。然后你可以这样做:

Insert into A(identity, fname, lname) SELECT newid, fname, lname FROM B

不确定您使用的是什么数据库但是对于sql server,打开身份插入的命令将是:

set identity_insert A on

答案 5 :(得分:0)

我建议使用uniqueidentifier类型而不是identity。在这种情况下,您可以在插入之前生成ID:

update B set NewID = NEWID()

insert into A(fname,lname,id) select fname,lname,NewID from B

答案 6 :(得分:0)

-- first create a table for show how its works
CREATE TABLE [dbo].[myTable]
  (
     [id]   [INT] IDENTITY(1, 1) NOT NULL,
     [text] [VARCHAR](10) NULL
  )
ON [PRIMARY]

GO

-- var table for keep new inserted id
DECLARE @tblNewInserted TABLE
  (
     newids INT
  )

--use the output clause in insert statement
INSERT INTO [dbo].[myTable]
output      inserted.id
INTO @tblNewInserted
VALUES      ('aa'),('bb'),('cc')

SELECT *
FROM   @tblNewInserted 

答案 7 :(得分:-7)

MBelly是对的 - 但是然后触发器将始终尝试更新表B,即使这不是必需的(因为你也是从表C插入?)。

Darren在这里也是正确的,你不能将多个身份作为结果集返回。您的选项是使用游标并为您插入的每一行获取标识,或使用Darren的方法在之前和之后存储标识。只要您知道身份的增量,这应该有效,只要您确保所有三个事件都锁定了表。

如果是我,并且时间不重要,我会使用光标。