ORA-01747:user.table.column,table.column或列规范无效

Ton*_*nyP 11 oracle plsql dynamic-sql

在循环中调用execute immediate时获取上述错误

Update CustomersPriceGroups set  1AO00=:disc  Where cuno=:cuno
    Parameters:   disc=66 cuno=000974
Update CustomersPriceGroups set  1AP00=:disc  Where cuno=:cuno
    Parameters:   disc=70.5 cuno=000974
Update CustomersPriceGroups set  1AQ00=:disc  Where cuno=:cuno
    Parameters:   disc=66 cuno=000974
Update CustomersPriceGroups set  1ZA00=:disc  Where cuno=:cuno
    Parameters:   disc=60 cuno=000974
Run Code Online (Sandbox Code Playgroud)

这是什么意思 ?

这是代码片段

    c:=PriceWorx.frcPriceListCustomers('020','221');
LOOP
  fetch c into comno,cuno,nama,cpls;
  exit when c%notfound;
  dbms_output.put_Line(cuno);
   g:=priceWorx.frcPriceListItemGroups('020','221');
   d:=priceworx.frcCustomerDiscounts('020','221',cuno);
  loop
    fetch g into comno,cpgs,n;
    fetch d into comno,cpls,cuno,cpgs,stdt,tdat,qanp,disc,src;
    --dbms_output.put(chr(9)||cpgs);
    sQ:='Update saap.CustomersPriceGroups set "'|| trim(cpgs)||'"=:disc '
       || ' Where cuno=:cuno';
    execute immediate sQ using disc,cuno; 
    commit;
    dbms_output.put_line( sQ );
    dbms_output.put_line( chr(9)||'Parameters:   disc='|| disc||' cuno='||cuno);
    exit when g%notfound;
  end loop;
  close g;
  close d;
end loop;
Run Code Online (Sandbox Code Playgroud)

yur*_*rin 26

检查您的查询是否有双逗号.

insert into TABLE_NAME (COLUMN1, COLUMN2,,COLUMN3) values(1,2,3);
Run Code Online (Sandbox Code Playgroud)

(COLUMN2之后还有额外的逗号).


更新:最近(有些人有特殊才能)我成功地用新方法得到了同样的例外:

update TABLE_NAME set COLUMN1=7, set COLUMN2=8
Run Code Online (Sandbox Code Playgroud)

(第二个SET是多余的)

  • 谢谢。我在第一个右括号前加了一个逗号)。Oracle 似乎并不费心提供好的错误消息。 (2认同)

nin*_*ded 7

这意味着Oracle解析器认为您的某个列无效.这可能是因为您错误地引用了列,列名称是保留字,或者因为您在UPDATE语句中出现语法错误,导致Oracle认为不是列的内容是列.查看正在执行的完整语句,CustomersPriceGroups表的定义以及引发异常的全文真的很有帮助,因为它通常会告诉哪个列有错.

  • 在我的情况下,列名是保留字. (4认同)
  • 在我的例子中,我在`insert`语句中有一个尾随逗号`,`. (2认同)

Ale*_*ole 6

不带引号的标识符必须以字母字符开头(请参阅此处的规则6).你试图将值分配给列一个名字开始与多家1AO00,1AP00等等.

在没有看到表定义的情况下,CustomersPriceGroups我们不知道它是否包含具有这些名称的列.如果是,则必须将它们创建为带引号的标识符.如果是这样,你将不得不用引号引用它们(无处不在),这是不理想的 - 使代码更难阅读,这样就容易犯这样的错误,并且很难发现错误.甚至Oracle也在同一页面上说:

注意:Oracle建议不要对数据库对象名称使用带引号的标识符.SQL*Plus接受这些带引号的标识符,但在使用管理数据库对象的其他工具时它们可能无效.

在您的代码中,您在分配时似乎使用引号sQ,但您显示的输出不是; 但它也没有saap.模式标识符.这可能是因为你没有运行你想到的代码版本,但是如果重新输入数据而不是粘贴数据可能会丢失 - 你没有显示c.cuno任何一个的早期输出.但是,例如,列名称的情况也可能是错误的.

如果execute抛出错误,你将看不到循环周围执行的命令,因为调试发生在它之后 - 你看到的是成功的值,而不是那个正在破坏的值.您需要检查函数返回的所有值; 我怀疑它g返回的值cpgs实际上不是有效的列名.

正如@ninesided所说,显示更多信息,特别是完整的异常消息,将有助于识别出错的原因.


Jun*_*Liu 5

如果在 set 语句末尾添加额外的“,”而不是语法错误,您将得到 ORA-01747,这对于 Oracle 来说非常非常奇怪,例如

  update table1 
  set col1 = 'Y', --this odd 1
  where col2 = 123
  and col3 = 456 
Run Code Online (Sandbox Code Playgroud)