0

我想使用不同的用户名和来自行类型的数据生成一个动态插入语句

我的片段

create or replace procedure test()
is
TYPE cv_typ is REF CURSOR;
cv cv_typ;
stmt varchar(2000);
zieldb varchar(20);

vKunden "Kunden"%rowtype;

BEGIN

execute immediate 'select * from "Kunden" where "KndNr"=55 ' into vKunden;

stmt:='select kc.zieldb from test.kunden_copy kc, test.transrel vd 
where kc.zieldb=vd.dbname and kc.status=1 ';

OPEN cv FOR stmt;
LOOP
    FETCH cv into nachdb;
    EXIT WHEN cv%NOTFOUND;
    ...
    ...
    stmt:='insert into ' || nachdb || ' ."Kunden"   values  ' || vKunden;
    execute immediate stmt ;        
    ...
    ... 
END LOOP;
END;

我收到以下错误消息:

Please-00306 调用中的参数数量或类型错误

使用以下语法

stmt:='insert into ' || nachdb || ' ."Kunden"   values   vKunden ';
execute immediate stmt ;        

我收到以下消息:

ORA-03001: 未实现的功能

4

2 回答 2

1

看来你不能这样做。在您的第一次尝试中,您尝试将 PL/SQL 记录类型(从%rowtype)连接到字符串;如果它让你那么它会放什么,它的记录的内部表示?为了使它成为一个有效的插入语句,它必须将它转换为记录中的值列表, as (col1, col2, ...),这要求相当多。

在您的第二个版本中,使用 ORA-03001,我认为这是因为它被解释vKunden为对象标识符;PL/SQL 块中的记录变量不在 SQL 语句的范围内。

大概您已经尝试为此使用绑定变量,但发现不能,因为绑定变量必须是 SQL 类型 (PLS-00457)。

您也许可以使用DBMS_SQL单步执行%rowtype变量并根据它包含的列/字段构建自己的values子句,但这似乎很痛苦。

据推测,尽管"Kunden"(引用的对象标识符?你不觉得使用起来很痛苦吗?) 的各种版本都是相同的,否则%rowtype你用来声明的东西vKunden无论如何都不会申请插入,所以你知道所有列名。您必须单独绑定每个列值:

stmt:='insert into ' || nachdb || ' ."Kunden" ("KndNr", "Col2", ...)'
    || ' values (:1, :2, ...)';
execute immediate stmt using vKunden."KndNR", vKunden."Col2", ...;

虽然更简单的是:

stmt:='insert into ' || nachdb || ' ."Kunden"'
    || ' select * from "Kunden" where "KndNr"=55';
execute immediate stmt;

...这完全绕过vKunden了这个%rowtype问题。您正在多次执行该选择,但这可能不是很大的开销

于 2013-08-09T12:16:23.883 回答
0

只是添加为什么它不起作用: 03001 是因为值周围没有括号 () 。即使有括号它也不起作用,因为 vKunden 是 %rowtype,所以你不能将它传递给动态 sql (pls-00457)。您可以使用以下方法进行检查: 使用 vKunden 立即执行 'select :1 from dual';

于 2016-06-21T09:45:31.607 回答