在Oracle中插入多行

use*_*564 12 sql oracle insert

在关于多行插入Oracle 的讨论中,展示了两种方法:

第一:

insert into pager (PAG_ID,PAG_PARENT,PAG_NAME,PAG_ACTIVE)
          select 8000,0,'Multi 8000',1 from dual
union all select 8001,0,'Multi 8001',1 from dual
Run Code Online (Sandbox Code Playgroud)

第二:

INSERT ALL
   INTO t (col1, col2, col3) VALUES ('val1_1', 'val1_2', 'val1_3')
   INTO t (col1, col2, col3) VALUES ('val2_1', 'val2_2', 'val2_3')
   INTO t (col1, col2, col3) VALUES ('val3_1', 'val3_2', 'val3_3')
   .
   .
   .
SELECT 1 FROM DUAL;
Run Code Online (Sandbox Code Playgroud)

有人会争辩使用一个而不是另一个吗?

PS我自己没有做过任何研究(甚至是解释计划),所以任何信息或意见都会受到赞赏.

谢谢.

Qua*_*noi 7

从性能的角度来看,这些查询是相同的.

UNION ALL不会损害性能,因为只有在需要时才会Oracle估计UNION'ed查询,它不会先缓存结果.

SELECT语法在这种意义上更灵活,SELECT如果你想改变某些东西,你可以更容易地进行查询.

例如,这个查询:

insert into pager (PAG_ID,PAG_PARENT,PAG_NAME,PAG_ACTIVE)
          select 8000,0,'Multi 8000',1 from dual
union all select 8001,0,'Multi 8001',1 from dual
Run Code Online (Sandbox Code Playgroud)

可以改写为

INSERT
INTO    pager (PAG_ID,PAG_PARENT,PAG_NAME,PAG_ACTIVE)
SELECT  7999 + level, 0, 'Multi ' || 7999 + level, 1
FROM    dual
CONNECT BY
        level <= 2
Run Code Online (Sandbox Code Playgroud)

通过2使用适当的数字替换,您可以获得所需的任意数量的行.

在这种情况下INSERT ALL,您将不得不复制目标表描述,如果您需要40行,则不太可读.


Kos*_*801 2

理论上,使用 的语句UNION ALL在性能上有一个小的缺点,因为它必须在插入发生之前合并所有语句的结果。没有INSERT ALL这个缺点,因为最终结果已经可以逐行处理。

但实际上 Oracle 内部的优化器应该使差异可以忽略不计,选择哪种方式取决于您的偏好。

在我看来,这INSERT ALL两种方法中人类可读性更好,而UNION ALL变体是自动生成此类插入时占用更少空间的一种。