2017-03-06 68 views
2

我试图在多对多关系的联结表中添加值。从多个表中查找具有另一个(唯一)字段的主ID

表看起来像这些(所有ID是整数):

表A

+------+----------+ 
| id_A | ext_id_A | 
+------+----------+ 
| 1 | 100 | 
| 2 | 101 | 
| 3 | 102 | 
+------+----------+ 

表B在概念上类似于

+------+----------+ 
| id_B | ext_id_B | 
+------+----------+ 
| 1 | 200 | 
| 2 | 201 | 
| 3 | 202 | 
+------+----------+ 

表PK是ID_A和ID_B ,因为我的联结表中的列对这些列是FK,但我必须插入具有值的值外部ID(ext_id_A,ext_id_B)。

外部ID是唯一的列(因此与表ID本身是1:1),所以具有ext_id我可以查找确切的行并获取需要插入到联结表的id。

这是我到目前为止已经做了一个例子,但看起来并不像一个优化的SQL语句:

-- Example table I receive with test values 
declare @temp as table (
    ext_id_a int not null, 
    ext_id_b int not null 
); 

insert into @temp values (100, 200), (101, 200), (101, 201); 

--Insertion - code from my sp 
declare @final as table (
    id_a int not null, 
    id_b int not null 
); 

insert into @final 
select a.id_a, b.id_b 
from @temp as t 
inner join table_a a on a.ext_id_a = t.ext_id_a 
inner join table_b b on b.ext_id_b = t.ext_id_b 

merge into junction_table as jt 
using @final as f 
on f.id_a = jt.id_a and f.id_b = tj.id_b 
when not matched by target then 
insert (id_a, id_b) values (id_a, id_b); 

我在想MERGE语句,因为我的存储过程中的数据接收表值参数参数,我也必须检查已经存在的引用。

我能做些什么来改善这些值的插入?

+1

这就是为什么他们教你在学校 – IsuruKusumal

+0

是的,我知道。我没有创建这些表正常化,但我一定要找到我的路反正 – Andrea

+0

那么你的方法有什么问题? –

回答

1

无需使用@final表变量:

; with cte as (
    select tA.id_A, tB.id_B 
    from @temp t 
    join table_A tA on t.ext_id_a = tA.ext_id_A 
    join table_B tB on t.ext_id_B = tB.ext_id_B 
) 
merge into junction_table 
using cte 
on cte.id_A = junction_table.id_A and cte.id_B = junction_table.id_B 
when not matched by target then 
insert (id_A, id_B) values (cte.id_A, cte.id_B); 
+0

我会接受你的答案,因为没有人回答,这似乎是一个很好的建议。我不知道临时表和cte之间的区别 - 所以我仍然感谢你 – Andrea

+1

是的,CTE是一个重要的概念,它有时非常方便;看看CTE的递归,它们非常强大。至于我的回答,我希望这是你想达到的目标......保重! –

相关问题