ORACLE存储过程习题及答案,题目是网上找的,答案是本人自己写的,仅供参考

 

建表语句:

员工表emp_test

create  table emp_test(

  Idnumber(5) notnullprimarykey,

  Emp_id number(10) notnull,

  Namevarchar2(200) notnull,

  Pay number(10,2default0,

  Dept_id varchar2(20) notnull,

  entryDate datedefaultsysdate

)

部门信息表dept_test

Create table dept_test(

Id number(5) not null primarykey,

Name varchar2(200) not null,

Loc varchar2(500)

)

insertinto emp_test values(3,10003,'李三',3500,5,to_date('20170302','yyyy/mm/dd'));

insertinto emp_test values(4,10004,'李四',4500,3,to_date('20170201','yyyy/mm/dd'));

insertinto emp_test values(5,10005,'李五',2500,4,to_date('20170102','yyyy/mm/dd'));

insertinto emp_test values(6,10006,'张一',5500,3,to_date('20170402','yyyy/mm/dd'));

insertinto emp_test values(7,10007,'张二',7500,7,to_date('20170205','yyyy/mm/dd'));

insertinto emp_test values(8,10008,'张三',7500,6,to_date('20170209','yyyy/mm/dd'));

insertinto emp_test values(9,10009,'张四',2500,8,to_date('20170112','yyyy/mm/dd'));

insertinto emp_test values(10,10010,'张五',12500,9,to_date('20170312','yyyy/mm/dd'));

insertinto emp_test values(11,10011,'白一',3500,10,to_date('20170209','yyyy/mm/dd'));

insertinto emp_test values(12,10012,'白二',6500,4,to_date('20170112','yyyy/mm/dd'));

insertinto emp_test values(13,10013,'白三',5500,9,to_date('20170310','yyyy/mm/dd'));

insertinto emp_test values(14,10014,'白四',8500,7,to_date('20170412','yyyy/mm/dd'));

insertinto emp_test values(15,10015,'白五',4500,10,to_date('20170212','yyyy/mm/dd'));

 

(1)     创建一个存储过程,以员工号为参数,输出该员工的工资  

create or replace procedure EMP_NUM_PAY(

       e_id in emp_test.emp_id%type,

       a_pay outemp_test.pay%type

 )

 is

 e_pay integer :=0;

 begin

    begin

      select pay intoe_pay from emp_test where emp_id  = e_id;

    end;

    --1)执行

    declare

        emp_idemp_test.emp_id%type := 10001;

    begin

      a_pay := e_pay;

     dbms_output.put_line(e_id || ' 员工的工资为:' ||e_pay);

    end;

 end EMP_NUM_PAY;

 

(2)      创建一个存储过程,以员工号为参数,修改该员工的工资。若该员工属于10号部门,  

--则工资增加150;若属于20号部门,则工资增加200;若属于30号部门,则工资增加250;  

--若属于其他部门,则增加300。  

createorreplaceprocedureupdate_emp_pay(e_id ininteger) as

E_dept_id integer;

E_pay varchar2(200);

begin

  begin

   Select dept_id

      Into e_dept_id

        From emp_test where emp_id=e_id;

    Select pay into e_pay fromemp_test where emp_id=e_id;

   dbms_output.put_line(e_id || ' 员工的工资调整前为:' || e_pay);

  end;

 

  begin

   If e_dept_id = 1  then

      Update emp_test set pay=(pay+150) where emp_id=e_id and dept_id=E_dept_id;

      Commit;

   Elsif e_dept_id = 2then

      Update emp_test set pay=(pay+200) where emp_id=e_id and dept_id=E_dept_id;

      Commit;

   Elsif e_dept_id = 3then

      Update emp_test set pay=(pay+250) where emp_id=e_id and dept_id=E_dept_id;

      Commit;

   Else

      Update emp_test set pay=(pay+300) where emp_id=e_id and dept_id=E_dept_id;

      Commit;

    Endif;

  End;

 

  Begin

    Select pay into e_pay fromemp_test where emp_id=e_id;

   dbms_output.put_line(e_id || ' 员工的工资调整后为:' || e_pay);

  End;

 

End update_emp_pay;

(3)  创建一个存储过程,以员工号为参数,返回该员工的工作年限(以参数形式返回)。  

create or replace procedureemp_work_year(e_id in integer,work_year out integer)is

Begin

Begin

     Select round((sysdate - entrydate),1) into work_year fromemp_test where emp_id=e_id;

end;

End emp_work_year;

Sql界面执行:

declare 

  e_idemp_test.emp_id%type := 10003

  v_year number

begin 

 emp_work_year(e_id,v_year); 

 dbms_output.put_line(e_id || ' 工作年限为 ' || v_year || ''); 

end;

(4)   创建一个存储过程,以部门号为参数,输出入职日期最早的10个员工信息。  

Create or replace emp_first(d_id in integer, cur_arg out sys_refcursor) is

Begin

      Begin

           open cur_arg for select * from emp_test whererownum<11 and dept_id=d_idorderby pay desc;

      End;

End emp_first;

 

 

declare

cur_calling sys_refcursor;

rec_next emp_test%rowtype;

begin

emp_first(3,cur_calling); --这样这个游标就有值了

loop

    fetch cur_calling

      into rec_next;

      exitwhen cur_calling%notfound;

   dbms_output.put_line('----------------:'|| rec_next.name ||'的工资为:'||rec_next.pay);

endloop;

closecur_calling;

end;

(5)   创建一个函数,以员工号为参数,返回该员工的工资。  

createorreplacefunctionemp_pay(e_id innumber) Returnnumber  is

E_pay  number;

Begin

  begin

       Select pay into E_pay from emp_test where emp_id=e_id;

       return E_pay;

  end;

End emp_pay;

(6)   创建一个函数,以部门号为参数,返回该部门的平均工资。 

Create orreplace function emp_dept_pay(d_id in number) return number  is

Result  number;

Begin

     Select dept_id,avg(nvl(pay,0))  intoresult from emp_test where dept_id=d_id;

Endemp_dept_pay;

 

(7)   创建一个函数,以员工号为参数,返回该员工所在的部门的平均工资。  

create orreplace function emp_dept_pay(d_id in number) return number  is

Result  number;

Begin

  Select avg(nvl(pay,0))  into result from emp_test where dept_id=d_id;

  return result;

Endemp_dept_pay;

(8)     创建一个存储过程,以员工号和部门号作为参数,修改员工所在的部门为所输入的部门号。  

--如果修改成功,则显示“员工由……号部门调入……号部门”;

--如果不存在该员工,则显示“员工号不存在,请输入正确的员工号。”;

--如果不存在该部门,则显示“该部门不存在,请输入正确的部门号。”。  

createorreplaceprocedureemp_change_dept(e_id integer,d_id integer) is

D_num integer;

Dd_id integer;

Begin

  Begin

  Select dept_id into dd_id fromemp_test where emp_id=e_id  groupby dept_id;

  EXCEPTION

  WHEN NO_DATA_FOUND THEN

   dbms_output.put_line(e_id||'员工号不存在,请输入正确的员工号');

    Return;

  End;

  begin

  Select id into d_num fromdept_test where id=d_id;

  EXCEPTION

  WHEN NO_DATA_FOUND THEN

    Dbms_output.put_line(d_id||'该部门不存在,请输入正确的部门号');

    Return;

  End;

  Begin

  Update emp_test set dept_id=d_id whereemp_id=e_id;

  Ifsql%rowcount =0then

   Dbms_output.put_line('部门变更失败');

  Else

   Dbms_output.put_line('员工由'||dd_id||'号部门调入'||d_id||'号部门');

  Endif;

  End;

End emp_change_dept;

(9)     创建一个存储过程,以一个整数为参数,输入工资最高的前几个(参数值)员工的信息。  

create or replace procedure emp_max_pay(numinteger) as

Begin

  For Iin (select * from (select * from emp_test order by pay desc) whererownum<=num)

  Loop

   Dbms_output.put_line(i.name||'的薪资为'||i.pay);

  Endloop;

End emp_max_pay;

Create or replace procedure emp_max_pay(numinteger, cur_arg outsys_refcursor) as

Begin

  Opencur_arg for  select * from (select * fromemp_test order by pay desc) where rownum<=num;

End emp_max_pay;

declare

cur_calling sys_refcursor;

rec_next emp_test%rowtype;

begin

emp_max_pay(3,cur_calling); --这样这个游标就有值了

loop

    fetch cur_calling

      into rec_next;

      exitwhen cur_calling%notfound;

   dbms_output.put_line('----------------:'|| rec_next.name ||'的工资为:'||rec_next.pay);

endloop;

closecur_calling;

end;

 

(10)   创建一个存储过程,以两个整数为参数,输出工资排序在两个参数之间的员工信息。  

createor replace procedure emp_range_pay(max_num integer,min_num integer)as

Begin

  For Iin (select * from emp_test where pay between min_num and max_num order by paydesc)

  Loop

   Dbms_output.put_line(i.name||'的薪资为'||i.pay);

  Endloop;

End emp_range_pay;

Create or replace procedure emp_range_pay(max_numinteger,min_num integer, cur_arg out sys_refcursor) as

Begin

  Opencur_arg for  select * from emp_test wherepay between min_num and max_num order by pay desc;

End emp_range_pay;

declare

cur_calling sys_refcursor;

rec_next emp_test%rowtype;

begin

emp_max_pay(3,cur_calling); --这样这个游标就有值了

loop

   fetch cur_calling

     into rec_next;

      exitwhen cur_calling%notfound;

   dbms_output.put_line('----------------:'|| rec_next.name ||'的工资为:'||rec_next.pay);

end loop;

close cur_calling;

end;

你可能感兴趣的:(oracle)