2017-06-22 103 views
0

我想创建一个接受两个表名作为参数的过程,然后将一个表中的行复制到另一个表中,一次一个。我知道批量插入和SELECT INTO是更好的方法来做到这一点,但批量插入不工作,因为当我插入多个行一次时,表触发抛出突变错误。PLSQL动态定义光标

我见过其他答案,推荐使用动态SQL,但我坚持如何定义游标的方式。

CREATE OR REPLACE PROCEDURE TABLE_INSERT(
    donor_t IN VARCHAR2, 
    empty_t IN VARCHAR2 
    ) 
AS 
    CURSOR C1 IS 
     SELECT * FROM donor_t; 
BEGIN 
    FOR row IN C1 
    LOOP 
     INSERT INTO empty_t VALUES row; 
    END LOOP; 
END; 

当编译为上面所写,编译器会引发ORA-00942: table or view does not exist.当用硬编码表名编制,该功能用于插入如预期中的行,没有错误。

+0

基本上你正在尝试做的是插入的选择,为什么不这样做呢? 逐行处理数据对性能非常不利。 –

+0

一种选择是查看触发器并考虑是否可以禁用批量操作,然后重新启用它们。很明显,您的批量操作需要处理由触发器执行的业务逻辑。否则,请尝试使用Oracle文档作为示例 - https://docs.oracle.com/cd/B28359_01/appdev.111/b28370/dynamic.htm#BHCGEFCA – BriteSponge

+1

@BriteSponge甚至没有发生过我看我是否可以禁用在插入后触发并重新启用它们;该解决方案就像一个魅力。 – OnLinedPaper

回答

1

试试这个:

CREATE OR REPLACE PROCEDURE TABLE_INSERT(
donor_t IN VARCHAR2, 
empty_t IN VARCHAR2 
) 
AS 
    V_SQL VARCHAR2(1000); 
BEGIN 
    V_SQL := 'INSERT INTO ' || empty_t || ' SELECT * FROM ' || donor_t; 
    EXECUTE IMMEDIATE V_SQL; 
END; 
/
+0

对于动态插入语句来说,这是一个很好的解决方案,但不幸的是它仍然导致触发器抛出突变错误,因为它并非一次一个插入。 – OnLinedPaper

+0

你可以分享触发器的代码吗? –