PLS-00302:必须声明组件-无法解析

Posted

技术标签:

【中文标题】PLS-00302:必须声明组件-无法解析【英文标题】:PLS-00302: component must be declared- Unable to resolve 【发布时间】:2014-03-10 16:53:00 【问题描述】:

我在 SQL developer 中尝试了以下程序并遇到了一些问题:

declare
  cursor emp_complex_cur is
    select e.fname,d.dlocation
      from employee e, dept_location d
     where e.dno=d.dnumber;
  emp_max_id integer;
  type emp_complex_rec is record(rname employee.fname%type,rlocation dept_location.dlocation%type);
begin
  open emp_complex_cur;
  for emp_complex_rec in emp_complex_cur loop
    fetch emp_complex_cur into emp_complex_rec;
    dbms_output.put_line('The employee id is: '||emp_complex_rec.rname||' and the employee''s location is '||emp_complex_rec.rlocation);
  close emp_complex_cur;
end;

我在声明变量 rname 时遇到错误,尽管它已在记录中正确声明。

【问题讨论】:

你应该考虑用这个创建一个sqlfiddle。 我相信 sqlfiddle 中没有可用的 Oracle 引擎。 @Rahul:SQLFiddle 肯定支持 Oracle。转到 sqlfiddle.com,单击数据库选择(默认为 mysql 5.5.32,但可以更改),然后在结果下拉列表中选择 Oracle 11g R2。分享和享受。 【参考方案1】:

试试:

begin
  for emp_complex_rec in (select e.fname,
                                 d.dlocation
                            from employee e
                            INNER JOIN dept_location d
                              ON (e.dno = d.dnumber))
  loop
    dbms_output.put_line('The employee id is: ' ||
                         emp_complex_rec.rname ||
                         ' and the employee''s location is ' ||
                         emp_complex_rec.rlocation);
  end loop;
end;

原始代码的问题在于 emp_complex_rec 作为类型的定义与 emp_complex_rec 作为游标循环变量的定义发生冲突。也不需要显式游标定义 - IMO 将 SELECT 放入 FOR 循环更容易和更清晰。

分享和享受。

【讨论】:

【参考方案2】:

光标中的列名称与您在输出行中调用的名称不同,我猜您使用的 for 循环会弄乱您的代码。实际上,它可能更简单:

declare
  cursor emp_complex_cur is
    select e.fname,d.dlocation
      from employee e, dept_location d
     where e.dno=d.dnumber;
  emp_max_id integer;
begin
  for emp_complex_rec in emp_complex_cur loop
    dbms_output.put_line('The employee id is: '||emp_complex_rec.fname||' and the employee''s location is '||emp_complex_rec.dlocation);
  end loop;
end;

【讨论】:

【参考方案3】:

您似乎混淆了几种不同的技术。


选项 #1 - 手动获取显式光标

declare
  cursor emp_complex_cur is
    select e.fname,d.dlocation
      from employee e, dept_location d
     where e.dno=d.dnumber;
  emp_max_id integer;
  type emp_complex_typ is record(rname employee.fname%type,rlocation dept_location.dlocation%type);
  --A variable must be declared of the type you've created
  emp_complex_rec emp_complex_typ;
begin
  open emp_complex_cur;
  --Initial fetch is needed
  fetch emp_complex_cur into r_complex_rec;
  while emp_complex_cur%found loop
    fetch emp_complex_cur into r_complex_rec;
  end loop;
  close emp_complex_cur;
  dbms_output.put_line('The employee id is: '||emp_complex_rec.rname||' and the employee''s location is '||emp_complex_rec.rlocation);
end;

选项 #2 - 使用 for 循环获取显式游标

declare
  cursor emp_complex_cur is
    select e.fname,d.dlocation
      from employee e, dept_location d
     where e.dno=d.dnumber;
begin
  --no "open" required
  for emp_complex_rec in emp_complex_cur loop
    --no "fetch" required
    null;
  end loop;
  --no "close" required
  dbms_output.put_line('The employee id is: '||emp_complex_rec.rname||' and the employee''s location is '||emp_complex_rec.rlocation);
end;

选项 #3 - 使用 for 循环获取隐式游标

查看@BobJarvis 提供的答案


选项 #4 - 仅获取一次显式游标

对于这种只检索单个记录的场景,我更喜欢使用显式游标和单个提取。如果您的查询返回 1 行或 100 行,这并不重要,因为您只对其中一个进行操作。为什么要遍历您要忽略的所有行?

declare
  cursor emp_complex_cur is
    select e.fname,d.dlocation
      from employee e, dept_location d
     where e.dno=d.dnumber;
  emp_complex_rec emp_complex_cur%rowtype;
begin
  open emp_complex_cur;
  fetch emp_complex_cur into r_complex_rec;
  close emp_complex_cur;
  dbms_output.put_line('The employee id is: '||emp_complex_rec.fname||' and the employee''s location is '||emp_complex_rec.dlocation);
end;

【讨论】:

感谢艾伦的详细解答!即使使用了选项 #1 中提到的记录类型,我仍然面临问题。我需要显示满足条件的所有行(员工表中的员工 ID=部门表中的员工 ID)。我试图通过选项#2 中提到的方式来实现这一点。但是当我运行选项 #2 中给出的代码时,我仍然遇到同样的错误。请问有什么想法吗?

以上是关于PLS-00302:必须声明组件-无法解析的主要内容,如果未能解决你的问题,请参考以下文章

PLS 00302:组件 DATA_TYPE 必须在函数中声明

PLS 00302:组件DATA_TYPE必须在函数中声明

必须声明组件错误 (ORA-06550)

React Native - 无法解析样式组件中的声明

Webpack 和 TypeScript 无法解析 Vue 的声明文件

当导入到 oracle 10g 得到错误 6550