我正在尝试创建一个SQL脚本来插入一个新行,并在插入另一个表时将该行的标识列用作FK。
这是我用于一对一关系的内容:
INSERT INTO userTable(name) VALUES(N'admin')
INSERT INTO adminsTable(userId,permissions) SELECT userId,255 FROM userTable WHERE name=N'admin'
但现在我也有一对多的关系,我问自己是否可以使用比这更少的SELECT查询:
INSERT INTO bonusCodeTypes(name) VALUES(N'1500 pages')
INSERT INTO bonusCodeInstances(codeType,codeNo,isRedeemed) SELECT name,N'123456',0 FROM bonusCodeTypes WHERE name=N'1500 pages'
INSERT INTO bonusCodeInstances(codeType,codeNo,isRedeemed) SELECT name,N'012345',0 FROM bonusCodeTypes WHERE name=N'1500 pages'
我也可以这样使用......
INSERT INTO bonusCodeInstances(codeType,codeNo,isRedeemed)
SELECT name,bonusCode,0 FROM bonusCodeTypes JOIN
(SELECT N'123456' AS bonusCode UNION SELECT N'012345' AS bonusCode)
WHERE name=N'1500 pages'
但这也是插入所有代码的一种非常复杂的方式,我不知道它是否更快。
那么,是否有可能在SQL语句中使用变量?像
var lastinsertID = INSERT INTO bonusCodeTypes(name) OUTPUT inserted.id VALUES(N'300 pages')
INSERT INTO bonusCodeInstances(codeType,codeNo,isRedeemed) VALUES(lastinsertID,N'123456',0)
答案 0 :(得分:1)
OUTPUT
只能插入表格中。如果您只插入单个记录,则使用SCOPE_IDENTITY()
会更方便,它保存最近插入的标识值的值。如果您需要一系列值,一种技术是将OUTPUT
所有标识值与业务键一起转换为临时表或表变量,并加入其中 - 但是如果要插入的表具有这些键上的索引(以及为什么不应该这样)除了更多的I / O之外,它只是简单地加入事务中的基表而没有任何收获。
所以,在你的例子中:
INSERT INTO bonusCodeTypes(name) VALUES(N'300 pages');
DECLARE @lastInsertID INT = SCOPE_IDENTITY();
INSERT INTO bonusCodeInstances(codeType,codeNo,isRedeemed) VALUES (@lastInsertID, N'123456',0);
SELECT @lastInsertID AS id; -- if you want to return the value to the client, as OUTPUT implies
而不是VALUES
,您当然可以加入桌面,只要您在任何地方都需要相同的@lastInsertID
值。
关于你原来的问题,是的,你也可以从语句中分配变量 - 但不能用OUTPUT
分配变量。但是,SELECT @x = TOP(1) something FROM table
完全没问题。