If statement IF语句不允许Select语句比较给定字符串

If statement IF语句不允许Select语句比较给定字符串,if-statement,select,plsql,If Statement,Select,Plsql,编写一个OraclePLSQL过程来执行以下任一操作:a更新表course并将输入课程名称的费用设置为等于java课程的费用。b为给定的输入课程插入新行,并设置表中所有可用课程的最低费用。条件是:如果输入课程名称已存在于表中,则执行a;如果输入课程名称不在表中,则执行b 我在此提供表的基本细节: create table course(cid number primary key, cname varchar2(100), duration number, fee number); insert

编写一个OraclePLSQL过程来执行以下任一操作:a更新表course并将输入课程名称的费用设置为等于java课程的费用。b为给定的输入课程插入新行,并设置表中所有可用课程的最低费用。条件是:如果输入课程名称已存在于表中,则执行a;如果输入课程名称不在表中,则执行b

我在此提供表的基本细节:

create table course(cid number primary key, cname varchar2(100), duration number, fee number);
insert into course (CID, CNAME, DURATION, FEE)
values (101, 'java', 30, 13000);

insert into course (CID, CNAME, DURATION, FEE)
values (102, 'c', 20, 5000);

insert into course (CID, CNAME, DURATION, FEE)
values (104, 'oracle', 20, 20000);

insert into course (CID, CNAME, DURATION, FEE)
values (105, 'python', 20, 30000);

insert into course (CID, CNAME, DURATION, FEE)
values (106, 'sql', 20, 1000);
我尝试了下面的代码,但我不知道如何比较IF语句中表中每行的给定名称。请看一下代码并帮助我

create or replace procedure proc_CourseFeeUpdateTry(coursename in course.cname%type,
                                                    java_fee   out number) is
  n_fee number;
  j_fee number;
begin
    if course.cname = coursename then --i'm getting error here

      select t.fee into j_fee from course t where t.cname = 'java';
      java_fee := j_fee;
      update course t set t.fee = java_fee where t.cname = coursename;
      dbms_output.put_line('new course added');
    else
      dbms_output.put_line(sqlerrm || '-' || sqlcode);
      select min(t.fee) into n_fee from course t;
      java_fee := n_fee;
      insert into course values (103, coursename, 40, java_fee);
    end if;
  commit;
end;

您得到的错误似乎源于对可用表数据的一个主要误解。IF语句允许后续选择没有问题。这里的问题是您引用了一个表列course.cname,而之前没有从course表中选择任何内容。因为表的存在并不能访问其中的数据,所以必须在引用列值之前进行选择。所以在此之前,如果你至少需要一个选择,因为这是一个选择的过程。。具体到。 现在,如果存在select into,则列值可用,但如果不存在,则抛出not_DATA_FOUND异常。我们必须承认这一事实,以避免这种情况。此外,还有两个实例可以使用该结构:

select data_value into local variable;
output_variable = local_variable; 
这是不必要的,因为您可以直接选择输出变量。 以下内容包含对您的程序的两个修订。第一,尽可能多地留下你的代码。第二次修订准则,以利用上述所有内容。我希望这有助于你进一步理解。 最低限度的必要更改要求您在IF语句之前选择课程表,并处理“未找到数据”错误

create or replace procedure proc_CourseFeeUpdateTry(coursename in course.cname%type,
                                                    java_fee   out number) is
  n_fee number;
  j_fee number;

  l_course_name   course.cname%type; 
begin
    begin
        select c.cname
          into l_course_name
          from course c
         where c.cname = coursename;
    exception 
    when no_data_found then 
       null; 
    end ; 

    if l_course_name = coursename then  

      select t.fee into j_fee from course t where t.cname = 'java';
      java_fee := j_fee;
      update course t set t.fee = java_fee where t.cname = coursename;
      dbms_output.put_line('course fee updated');       --- course was not added just updted
    else
      dbms_output.put_line(sqlerrm || '-' || sqlcode);
      select min(t.fee) into n_fee from course t;
      java_fee := n_fee;
      insert into course values (103, coursename, 40, java_fee);  --- leave message
      dbms_output.put_line('new course added');
    end if;
  commit;
end;
第二个版本使用了上面提到的主题和结构

create or replace procedure proc_CourseFeeUpdateTry(coursename in course.cname%type,
                                                    java_fee   out number) is

  l_cid course.cid%type; 
begin
    select c.cid 
      into l_cid  
      from course c
     where c.cname = coursename; 

    begin  -- inner block to trap java not found 
       -- if we get here then we know that the implied test cource.cname = coursename is true
       select t.fee into java_fee
         from course t where t.cname = 'java';

       update course t set t.fee = java_fee where cid = l_cid;
       dbms_output.put_line( coursename || ' fee updated');
       commit;
    exception 
      when no_data_found then 
         raise_application_error( -20109, 'course name ''java'' is not in course table');
      end ; -- inner block

exception
when no_data_found then
   -- if we get here the we know that the course name does not exist 
   select min(t.fee) into java_fee from course t;
   insert into course values (103, coursename, 40, java_fee);
   commit; 
end;

请注意这两个过程中的插入。它对id进行了硬编码。因此,您的过程能够精确地添加一行1次。这是一个极其糟糕的过程。将新id作为参数传递仍然不好,但更好,或者重新定义表以自动生成密钥。根据您的Oracle版本,查找序列和在12c之前插入触发器或标识列12c及更高版本

有几件事可能会阻止你得到你想要的帮助。1张贴代码图片不如张贴代码。请编辑您的问题以添加格式良好的代码2您没有标记任何语言,这将限制有多少人看到您的问题,3最好只问一个精确的问题并解决这个问题,而不是一次问几个问题。我真的很抱歉!我是这个堆栈溢出的新手,对在这里发布不太了解。我的问题与oracle plsql.Lease review有关。以此作为你问题的模板,大大提高了你获得满意答案的机会。在这种情况下,永远不要发布图像。还包括样本数据和该数据的预期输出,同样在文本中,没有图像。用你想完成的任务来描述你的问题。嗨,我修改了我的问题。请看一看。谢谢你的解释。但是告诉我,如果select返回多行,我们会使用游标吗?那么我们如何比较IF语句中的每个值呢?如果返回的行超过1行,您可以使用游标,然后必须将处理放入循环中。。。结束循环构造。这将分别处理每一行。但是,在这种情况下,不应尝试处理返回的多行。这将表明一个主要的数据库问题。没有其他列的Select min返回1行-可能为空。其他人选择至少应该是唯一的。如果JAVA或任何其他课程名称存在不止一次,您会怎么做?最好的过程始终在这里。只处理你该做的那些错误(你知道该怎么做)。对于所有其他错误,请创建一个日志条目并重新引发错误或忽略它,它将传播到调用进程。如果我有重复的课程,那么对于选择费用,我会像coursname=java和courseid=2一样对其进行筛选。。。那会给我一笔费用。回答错了。你有数据问题。你需要解决这个问题。顺便说一句,使用您提供的coursename='java'和courseid=2的数据,将找不到任何数据。但做你想做的事,经验是一个严酷的任务大师,但它会教你。