如何用动态SQL实现按列查询特殊字符并解决PL/SQL报错
解决PL/SQL动态SQL执行正则查询的ORA-06550报错问题
你遇到的ORA-06550/PLS-00103报错,根源是动态SQL拼接时正则表达式的模式字符串单引号没有正确转义。原代码里的','[A-Za-z0-9.]'部分,第二个单引号直接结束了动态SQL的字符串常量,导致后面的[被PL/SQL解析成无效符号,触发语法错误。
下面提供两种解决方法:
方法1:修正单引号转义
在PL/SQL的字符串中,要表示一个单引号,必须写成两个连续的单引号。把原动态SQL里的正则模式部分的单引号转义即可:
DECLARE r_emp SYS.ODCINUMBERLIST := SYS.ODCINUMBERLIST(); v_array SYS.ODCIVARCHAR2LIST := SYS.ODCIVARCHAR2LIST( 'cust_name', 'BILL_DELIVER_METHOD' ); BEGIN DBMS_OUTPUT.ENABLE; FOR i IN 1..v_array.COUNT LOOP r_emp.EXTEND; EXECUTE IMMEDIATE 'SELECT COUNT(1) FROM customer_profile WHERE NOT REGEXP_LIKE('||v_array(i)||',''[A-Za-z0-9.]'')' INTO r_emp(i); DBMS_OUTPUT.PUT_LINE(v_array(i) || ': ' || r_emp(i)); END LOOP; END; /
关键修改:把','[A-Za-z0-9.]'改成',''[A-Za-z0-9.]'',用两个单引号转义模式字符串的前后单引号。
方法2:使用绑定变量(更安全,推荐)
避免直接拼接字符串,改用绑定变量传递正则模式,既避免语法问题,还能防止SQL注入风险:
DECLARE r_emp SYS.ODCINUMBERLIST := SYS.ODCINUMBERLIST(); v_array SYS.ODCIVARCHAR2LIST := SYS.ODCIVARCHAR2LIST( 'cust_name', 'BILL_DELIVER_METHOD' ); v_pattern VARCHAR2(100) := '[A-Za-z0-9.]'; BEGIN DBMS_OUTPUT.ENABLE; FOR i IN 1..v_array.COUNT LOOP r_emp.EXTEND; EXECUTE IMMEDIATE 'SELECT COUNT(1) FROM customer_profile WHERE NOT REGEXP_LIKE('||v_array(i)||', :pattern)' INTO r_emp(i) USING v_pattern; DBMS_OUTPUT.PUT_LINE(v_array(i) || ': ' || r_emp(i)); END LOOP; END; /
这里把正则模式定义成变量v_pattern,在动态SQL里用:pattern作为绑定占位符,通过USING子句传递值,更规范也更安全。
内容的提问来源于stack exchange,提问作者Aman
相关产品推荐
相关产品推荐

