在PLSQL中操作数据转化过程中经常会用到MERGE语句,
MERGE函数是Oracle9i新增的函数,基本上就是等于update和insert两个函数的相加。使用MERGE函数,通过判断两个表之间某字段的关联情况,如果关联匹配上的话就进行update操作,如果没有匹配就执行insert。这个函数一来是减少了程序的长度,而且只对表进行一次全表扫描,效率也会有所提高。
1、
简单举例:
create
table
t1_a
as
select
rownum
id
,table_name
name
from
user_tables;
create
table
t1_b
as
select
rownum
id
,table_name
name
from
user_tables
where
table_name
like
'T%'
;
--
比
t1_a
记录少
merge
into
t1_b
using
t1_a
on
(t1_b.name = t1_a.name)
when
matched
then
update
set
t1_b.id = t1_b.id +
100000
when
not
matched
then
insert
values
(t1_a.id, t1_a.name);
--t1_b
表中没有的记录插入,有的记录把
id+100000
注:被修改的必然是在前面的表,后面的表是附加进来进行判断的。
2、只写一半:
假设在匹配时不想进行操作,则:
merge
into
t1_b
using
t1_a
on
(t1_b.name = t1_a.name)
--when matched then
-- update set t1_b.id = t1_b.id
when
not
matched
then
insert
values
(t1_a.id, t1_a.name);
如果使用9i版本,此时报错:ORA-00905: missing keyword
如果使用10g,则顺利执行。
3、多值报错:
truncate
table
t1_a;
truncate
table
t1_b;
insert
into
t1_a
values
(
1
,
'a'
);
insert
into
t1_b
values
(
1
,
'c'
);
insert
into
t1_b
values
(
1
,
'b'
);
commit
;
select
*
from
t1_a;
select
*
from
t1_b;
merge
into
t1_a
using
t1_b
on
(t1_b.id = t1_a.id)
when
matched
then
update
set
t1_a.name = t1_b.name
when
not
matched
then
insert
values
(t1_b.id, t1_b.name);
--ORA-30926: unable to get a stable set of rows in the source tables
4、不能修改作为关联的列
truncate
table
t1_a;
truncate
table
t1_b;
insert
into
t1_a
values
(
1
,
'a'
);
insert
into
t1_b
values
(
1
,
'b'
);
commit
;
merge
into
t1_a
using
t1_b
on
(t1_b.id = t1_a.id)
when
matched
then
update
set
t1_a.id = t1_b.id
when
not
matched
then
insert
values
(t1_b.id, t1_b.name);
--ORA-00904: "T1_A"."ID": invalid identifier
-The End-