0

问题:创建一个 Doctor 表(Docname、Qualification、Specialization、Working_shift)。考虑到当天的专业化和工作班次,使用参数化光标检查医生是否有空来为患者服务

我只是在学习数据库,所以如果这个问题看起来微不足道,我为此道歉。

在输入值时获得所需的输出,但我需要另一种方法来解决问题而不使用标志变量(这样我就可以得到异常)......如果我不使用标志,它会打印异常以及文件名和资格

我正在使用 oracle(普通 pl/sql 块中的光标)来执行此查询。

解决方案:

  --table creation

  create table doctor
  (
  docname varchar2(20),
  qualification varchar2(20),
  specialization varchar2(20),
  shift varchar2(20)
  )

我的解决方案

declare
    cursor c1 (specialization varchar2,shift varchar2) is select docname,qualification      from doctor
    where specialization='&sp' and shift='&shift'
    sp doctor.specialization%type;
    shift doctor.shift%type;
    flag number(10);
begin
    flag:=0;
    for r1 in c1(sp,shift)
    loop
        if c1%found then
            flag:=1;
            dbms_output.put_line('Doctor is available');
            dbms_output.put_line('Docname: '||r1.docname);
            dbms_output.put_line('qualification: '||r1.qualification);
        else
            flag:=0;
        end if;
    end loop;
    if flag=0 then
         dbms_output.put_line('Invalid specialization/shift');
    end if;
end;
4

3 回答 3

0

If you do not use parameters in "c1" cursor you do not need it...

DECLARE
    CURSOR c1 IS
        SELECT  docname, qualification
        FROM    doctor
        WHERE   specialization = '&sp'
        AND     shift          = '&shift';

    TYPE c1_ntt IS TABLE OF c1%ROWTYPE;
    l_c1  c1_ntt;
BEGIN
    OPEN  c1;
    FETCH c1 BULK COLLECT INTO l_c1;
    CLOSE c1;

    IF l_c1.COUNT = 0 THEN
        RAISE_APPLICATION_ERROR(-20000, 'Invalid specialization/shift');
    END IF;

    FOR indx IN l_c1.FIRST..l_c1.LAST LOOP
        DBMS_OUTPUT.PUT_LINE('Doctor is available');
        DBMS_OUTPUT.PUT_LINE('Docname: '       || l_c1(indx).docname);
        DBMS_OUTPUT.PUT_LINE('qualification: ' || l_c1(indx).qualification);
    END LOOP;
END;
于 2013-08-22T08:29:33.177 回答
0
  1. 您不需要在循环中重置标志,您已经0在程序开始时将其初始化。

  2. 您不需要检查c1%found,因为您在循环中;根据定义,找到了一条记录,否则它不会进入您的循环代码。

  3. 您的游标应该使用提供的变量,而不是 SQL*Plus 替换变量,例如:

    cursor c1 (specialization varchar2,shift varchar2) is
      select docname,qualification
      from doctor
      where doctor.specialization=c1.specialization
      and doctor.shift=c1.shift;
    

    如果您不想使用所有这些别名,则可以使用命名约定来区分不同的标识符(移位与移位),例如:

    cursor c1 (i_specialization varchar2, i_shift varchar2) is
      select docname,qualification
      from doctor
      where specialization=i_specialization
      and shift=i_shift;
    

    另请注意,您在查询末尾错过了一个分号。

最后:

如果您按如下方式更改循环,它应该可以正常工作:

for r1 in c1(&sp,&shift)
loop
    flag:=1;
    dbms_output.put_line('Doctor is available');
    dbms_output.put_line('Docname: '||r1.docname);
    dbms_output.put_line('qualification: '||r1.qualification);
end loop;

现在,您的最后一段代码:

if flag=0 then
     dbms_output.put_line('Invalid specialization/shift');
end if;

会正常工作 - 它只会在标志仍然存在时执行0(即查询未找到行)。

于 2013-08-22T05:03:39.423 回答
0

试试下面给出的代码

declare
cursor c1 (specialization varchar2,shift varchar2)
is 
select docname,qualification      
from doctor
where specialization='&sp' 
and shift='&shift'
sp doctor.specialization%type;
shift doctor.shift%type;
flag number(10);

begin
flag:=0;
for r1 in c1(sp,shift)
loop
    if c1%found then
        flag:=1;
        dbms_output.put_line('Doctor is available');
        dbms_output.put_line('Docname: '||r1.docname);
        dbms_output.put_line('qualification: '||r1.qualification);
    else
        raise;
    end if;
end loop;
exception

when others then
dbms_output.put_line('Invalid specialization/shift');

end;
于 2013-08-21T19:49:14.723 回答