首页 > 解决方案 > 在 Oracle PL/SQL 中使用 OPEN...FOR 动态 SQL 结构时多次重复相同的绑定变量

问题描述

这是对 Vincent Malgrat对这个问题的回答的后续问题。OPEN...FOR当您在使用动态 SQL时需要多次使用同一个绑定变量时,我找不到要使用的正确语法。EXECUTE IMMEDIATE 您可以在此处查看语法(请参阅“将重复占位符与动态 SQL 一起使用”)……但对于OPEN...FOR. 使用时语法是否与重复的占位符不同OPEN...FOR?我正在使用 Oracle 12c。这是在 PL/SQL 包中,而不是匿名块。

例如,Oracle 自己的文档中的这个示例可以正常工作:

DECLARE
   TYPE EmpCurTyp IS REF CURSOR;
   emp_cv   EmpCurTyp;
   emp_rec  emp%ROWTYPE;
   sql_stmt VARCHAR2(200);
   my_job   VARCHAR2(15) := 'CLERK';
BEGIN
   sql_stmt := 'SELECT * FROM emp WHERE job = :j';
   OPEN emp_cv FOR sql_stmt USING my_job;
   LOOP
      FETCH emp_cv INTO emp_rec;
      EXIT WHEN emp_cv%NOTFOUND;
      -- process record
   END LOOP;
   CLOSE emp_cv;
END;
/

但是,如果您需要:j多次引用绑定变量,那么在这种情况下,您将如何做到这一点,其中:j引用了两次?

sql_stmt := 'SELECT * FROM emp WHERE (job = :j AND name = :n) OR (job = :j AND age = :a)' ;

我努力了

OPEN emp_cv FOR sql_stmt USING my_job, my_name, my_age;

OPEN emp_cv FOR sql_stmt USING my_job, my_name, my_age, my_job;

在这两种情况下,它都会出现此错误:

ORA-01008: not all variables bound

标签: oracleplsqldynamic-sql

解决方案


您需要在 USING 子句中包含两次参数:

 OPEN emp_cv FOR sql_stmt USING my_job, my_job;

这是您的示例,但已简化:

DECLARE
   TYPE EmpCurTyp IS REF CURSOR;
   emp_cv   EmpCurTyp;
   emp_rec  varchar2(10);
   sql_stmt VARCHAR2(200);
   my_job   VARCHAR2(15) := 'X';
BEGIN

   OPEN emp_cv FOR 'select * from dual where dummy = :j or dummy = :j' 
    USING my_job, my_job;
   LOOP
      FETCH emp_cv INTO emp_rec;
      EXIT WHEN emp_cv%NOTFOUND;
   END LOOP;
   CLOSE emp_cv;
END;

推荐阅读