当我尝试在update语句中插入变量时,在Oracle中缺少表达式

时间:2014-04-17 01:25:13

标签: sql oracle

我正在尝试创建一个更新,它将使用我声明的变量更新表,但它给出了一个错误,表示"缺少表达式"。我对可能导致这种情况的原因感到茫然。

这是我的代码。

DECLARE
 VBILL BILL%ROWTYPE;
 CURSOR BILLAMT IS
  SELECT * FROM BILL;
 VCUST1 NUMBER(3);
 VCUST2 NUMBER(3);
 VCUST3 NUMBER(3);

BEGIN

 SELECT FREQUENCY INTO VCUST1 FROM RANGEOFBILLS WHERE RANGE=100;
 SELECT FREQUENCY INTO VCUST2 FROM RANGEOFBILLS WHERE RANGE=1000;
 SELECT FREQUENCY INTO VCUST3 FROM RANGEOFBILLS WHERE RANGE=10000;
 OPEN BILLAMT;
 LOOP
  FETCH BILLAMT INTO VBILL;
  EXIT WHEN BILLAMT%NOTFOUND;
  DBMS_OUTPUT.PUT_LINE(VBILL.AMOUNT);
  IF VBILL.AMOUNT>100 and VBILL.AMOUNT<=1000 THEN
   VCUST1:=VCUST1+1;
   EXECUTE IMMEDIATE('UPDATE RANGEOFBILLS SET FREQUENCY=@VCUST1 WHERE RANGE=100');
   DBMS_OUTPUT.PUT_LINE(VBILL.AMOUNT);
  END IF;
 END LOOP;
 CLOSE BILLAMT;
END;

我认为问题在于执行立即声明。我甚至试过这个:

EXECUTE IMMEDIATE ('UPDATE RANGEOFBILLS SET FREQUENCY=:a WHERE RANGE=100' USING VCUST1);

2 个答案:

答案 0 :(得分:2)

从第二次尝试中删除括号:

EXECUTE IMMEDIATE 'UPDATE RANGEOFBILLS SET FREQUENCY=:a WHERE RANGE=100'
USING VCUST1;

但是不需要动态SQL,最好使用UPDATE RANGEOFBILLS SET FREQUENCY=vcust1 WHERE RANGE=100;。此外,通常最好避免CURSOR / OPEN / FETCH / EXIT WHEN / CLOSE。隐式游标for循环更简单,更快:

DECLARE
 VCUST1 NUMBER(3);
 VCUST2 NUMBER(3);
 VCUST3 NUMBER(3);
BEGIN
 SELECT FREQUENCY INTO VCUST1 FROM RANGEOFBILLS WHERE RANGE=100;
 SELECT FREQUENCY INTO VCUST2 FROM RANGEOFBILLS WHERE RANGE=1000;
 SELECT FREQUENCY INTO VCUST3 FROM RANGEOFBILLS WHERE RANGE=10000;
 FOR VBILL IN (SELECT * FROM BILL) LOOP
  DBMS_OUTPUT.PUT_LINE(VBILL.AMOUNT);
  IF VBILL.AMOUNT>100 and VBILL.AMOUNT<=1000 THEN
   VCUST1:=VCUST1+1;
   UPDATE RANGEOFBILLS SET FREQUENCY=vcust1 WHERE RANGE=100;
   DBMS_OUTPUT.PUT_LINE(VBILL.AMOUNT);
  END IF;
 END LOOP;
END;
/

答案 1 :(得分:2)

DML语句不需要EXECUTE IMMEDIATE。只是做

UPDATE RANGEOFBILLS SET FREQUENCY = VCUST1 WHERE RANGE = 100;

而且我不确定你要做什么,但我想你可以在没有循环的单UPDATE语句中做到这一点,这会使它更有效率。