TSQL将2个Ids合并到临时表中

时间:2017-04-27 15:24:49

标签: sql sql-server tsql

我正在使用SQL Server 2012上的TSQL中的存储过程。当我调用存储过程时。我的问题:我正在将值插入到表Projects中,并希望将inserted.ProjectIdoID一起存储到导入表中的临时表中;我不会将导入表中的oID存储到Projects表中。

我指的是这个答案: Insert Into... Merge... Select (SQL Server)

1)导入表:我正在使用以下值从C#向SQL发送表:

oID |  Title   | 
----+----------+
 0  | ProjectX |
 1  | ProjectY |
 2  | ProjectZ |

在存储过程中看起来像这样:

CREATE TYPE [MySchema].[Project] AS TABLE
(
    oID INT,
    Title VARCHAR(100)
);

@ImportProjects MySchema.Project READONLY

2)项目表:我正在将值插入表项目中,并希望将inserted.ProjectId以及导入表中的oID存储到临时表中:

ProjectId |  Title   | 
----------+----------+
33        | ProjectX |
34        | ProjectY |
35        | ProjectZ |

3)所需的输出,临时表:在我的临时表中,我想存储ProjectId以及导入表中的oID:

 RowID  | oID |  ProjectId   | 
--------+-----+--------------+
1       |  0  | 33           |
2       |  1  | 34           |
3       |  2  | 35           |

我的合并查询如下所示:

create table Temp (ProjectId INT, oID INT)

MERGE INTO Temp USING
(
    SELECT 
        a.oID as oID,
        b.ProjectId as ProjectId
    FROM @ImportProjects a
    CROSS JOIN Projects b
) AS s ON 1 = 0
WHEN NOT MATCHED THEN
INSERT (oID, ProjectId)
VALUES (s.oID, s.ProjectId)
OUTPUT Inserted.ProjectId, s.oID
INTO Temp(oID, ProjectId);

这不起作用......我的一个问题当然是交叉连接,但我在导入表和项目表之间没有链接或外键...

你知道如何实现这个目标吗?

谢谢!! :)

2 个答案:

答案 0 :(得分:1)

CROSS JOIN替换为INNER JOIN。内部联接不会重新加入外键

create table Temp (ProjectId INT, oID INT)

MERGE INTO Temp USING
(
    SELECT 
        a.oID as oID,
        b.ProjectId as ProjectId
    FROM @ImportProjects a
    INNER JOIN JOIN Projects b ON a.Title = b.Title
) AS s ON 1 = 0
WHEN NOT MATCHED THEN
INSERT (oID, ProjectId)
VALUES (s.oID, s.ProjectId)
OUTPUT Inserted.ProjectId, s.oID
INTO Temp(oID, ProjectId);

答案 1 :(得分:1)

您的merge尝试有点令人困惑,但我认为这是您想要的:

create table tvp (oid int, Title varchar(100));
insert into tvp values (0,'ProjectX'),(1,'ProjectY'),(2,'ProjectZ');

create table #tmp (
    Id int not null identity(1,1)
  , oid int
  , ProjectId int
  , Title varchar(100)
);
create table Project (
    ProjectId int not null identity(33,1)
  , Title varchar(100)
);

merge into Project as Target
using tvp as Source
  on 1 = 0
when not matched then
insert (Title)
  values (source.Title)
output source.oid, Inserted.ProjectId, Inserted.Title
into #tmp;

select * from #tmp;

rextester演示:http://rextester.com/PIRFA34601

返回:

+-----+-----+-----------+----------+
|  Id | oid | ProjectId |  Title   |
+-----+-----+-----------+----------+
|   1 |   0 |        33 | ProjectX |
|   2 |   1 |        34 | ProjectY |
|   3 |   2 |        35 | ProjectZ |
+-----+-----+-----------+----------+

Rextester不支持表类型(因为它们不能在同一个事务中声明和使用),所以我使用了表tvp