zoukankan      html  css  js  c++  java
  • PLSQL函数,存储过程

      1 --创建一个函数,用来根据部门编号返回调薪幅度
      2 create or replace function get_ratio_by_dept(deptno varchar2)
      3      return number is
      4      n_salaryratio number(10,2);        --调薪比率返回值变量
      5 begin
      6      case deptno 
      7          when 10  then
      8              n_salaryratio:=1.09;
      9           when 20  then
     10              n_salaryratio:=1.11;
     11            when 30 then
     12               n_salaryratio:=1.18;
     13             else
     14               n_salaryratio:=0;
     15            end case;
     16            return n_salaryratio;
     17            end;   
     18 
     19 begin
     20   dbms_output.put_line(get_ratio_by_dept(20));
     21   end;   
     22 
     23  --创建一个存储过程,用来实现加薪,它将调用get_ratio_by_dept来获取加薪幅度
     24 
     25  create or replace procedure raise_salary(p_empno number)
     26  as 
     27      v_deptno number(2);
     28      v_ratio number(10,2);   --存储调薪幅度变量
     29   begin
     30     select deptno into v_deptno from emp where empno=p_empno;
     31     v_ratio:=get_ratio_by_dept(v_deptno);
     32     if v_ratio>0
     33       then 
     34         update scott.emp
     35             set sal =sal* (1+v_ratio)
     36         where empno = p_empno;
     37         end  if;
     38         dbms_output.put_line('加薪成功!');
     39   exception
     40      when no_data_found then
     41           dbms_output.put_line('没有找到该员工的任何信息!');
     42       when others then
     43           dbms_output.put_line('调整薪资时出现了错误!');             
     44     end;         
     45 
     46   set serveroutput on;  
     47   exec raise_salary(7369);   
     48 
     49 --创建包头
     50  create or replace package emp_sal_pkg as
     51  function get_ratio_by_dept(deptno varchar2) return number;
     52  procedure raise_salary(p_empno number);
     53  end emp_sal_pkg;
     54 
     55  --创建包体  
     56  create or replace package body emp_sal_pkg as
     57       function get_ratio_by_dept(deptno varchar2)
     58         return number
     59         is 
     60         n_salaryratio number(10,2);
     61         begin
     62           case deptno 
     63          when 10  then
     64              n_salaryratio:=1.09;
     65           when 20  then
     66              n_salaryratio:=1.11;
     67            when 30 then
     68               n_salaryratio:=1.18;
     69             else
     70               n_salaryratio:=1;
     71            end case;
     72            return n_salaryratio;
     73           end get_ratio_by_dept;
     74 
     75           procedure  raise_salary (p_empno number)
     76             as 
     77             v_deptno number(2);
     78             v_ratio number(10,2);
     79           begin
     80              select deptno into v_deptno from emp where empno=p_empno;
     81     v_ratio:=get_ratio_by_dept(v_deptno);
     82     if v_ratio>0
     83       then 
     84         update scott.emp
     85             set sal =sal* (1+v_ratio)
     86         where empno = p_empno;
     87         end  if;
     88         dbms_output.put_line('加薪成功!');
     89   exception
     90      when no_data_found then
     91           dbms_output.put_line('没有找到该员工的任何信息!');
     92       when others then
     93           dbms_output.put_line('调整薪资时出现了错误!');        
     94             end raise_salary;
     95             end emp_sal_pkg;  
     96 --创建过程添加新员工
     97  create or replace  procedure  AddNewEmp(p_empno emp.empno%type,
     98  p_ename emp.ename%type,
     99  p_job   emp.job%type,
    100  p_sal   emp.sal%type,
    101  p_deptno  emp.deptno%type:=20)
    102  as
    103  begin
    104    if p_empno<0 then
    105      raise_application_error(-20001,'员工编号必须大于0');
    106      end if;
    107        insert into emp
    108            (empno,ename,job,sal,deptno)
    109            values (p_empno,p_ename,p_job,p_sal,p_deptno);   
    110    end AddNewEmp;          
    111 
    112 begin
    113     AddNewEmp(8236,'诸葛亮','策划人员',25000,40);
    114     end;
    115 
    116 
    117 
    118 子程序创建高度可维护,重用的代码
    119 (1)模块化代码(2)简化应用程序(3)提升管理性:需求变更,只要改子程序
    120 (4)可重用性,提高性能
    121 程序调试
    122 C+R  直接运行  C+N单击进入  C+O单步逃过 C+T单步退出
    123 --在过程中使用return语句
    124 create or replace procedure RaiseSalary(
    125        p_empno emp.empno%type) as
    126        v_job emp.job%type;
    127        v_sal emp.sal%type;
    128 begin
    129     select job,sal into v_job,v_sal from emp
    130     where empno=p_empno;
    131     if v_job<>'CLERK' then
    132        return;               --如果不是职员则退出
    133      elsif v_sal>3000 then
    134        return ;
    135      else
    136        --否则更新薪资记录
    137       update emp set sal=Round(sal*1.12,2)  where
    138         empno=p_empno;
    139       end if;
    140   exception
    141      when no_data_found then
    142       dbms_output.put_line('没有找到员工记录');         
    143 end RaiseSalary;
    144 begin
    145   RaiseSalary(7369);
    146   end;
    147  select * from emp where empno=7369; 
    148 --查询当前scott方案下的过程和函数列表
    149 select object_name,object_type,created,
    150 last_ddl_time,status,temporary
    151        from user_objects
    152        where object_type in ('PROCEDURE','FUNCTION','TABLE');
    153 
    154 
    155 --in  out 模式参数
    156 create or replace procedure calcRaiseSalary(
    157        p_job in varchar2,
    158        p_salary in out number
    159 )    as  
    160  v_sal number(10,2); 
    161  v_job varchar2(10);
    162 begin
    163   if p_job='CLERK' then
    164     v_sal:=p_salary*1.12;
    165 
    166    elsif p_job='销售人员' then
    167      v_sal:=p_salary*1.18;
    168    elsif p_job='经理' then
    169      v_sal:=p_salary*1.19;
    170    else
    171      v_sal:=p_salary;
    172 
    173    end if;
    174        p_salary:=v_sal;  ---值传递
    175 
    176     end calcRaiseSalary;       
    177 
    178  declare
    179     v_sal number(10,2);
    180     v_job varchar2(10);
    181  begin
    182     select sal,job into v_sal,v_job from emp where
    183     empno=7369;
    184     calcRaiseSalary(v_job,v_sal);
    185     dbms_output.put_line('计算后的调整薪水为:'||v_sal);  --||'JOB'||v_jo
    186     end;
    187 
    188  select * from emp where empno=7369; 
    189 
    190  引用传递:将实际参数的指针(内存地址)传递给形式参数,
    191  值传递:将实际参数的值赋给形式参数,值拷贝,指向不同的内存地址
    192 
    193  如果参数是大型数据结构,比如集合,记录和对象实例, 参数复制会大大降低执行速度,
    194  消耗内存
    195 nocopy 使得out和in out模式的参数按引用进行传递
    196 
    197 
    198 
    199 
    200 
    201 
    202    --编译包规范
    203   alter package emp_pkg_overloading  compile specification;
    204   --编译包体
    205   alter package emp_pkg_overloading compile body;   
    206   --同时编译包规范和包体
    207   alter package emp_pkg_overloading compile package;
    208 
    209   --查询包规范和包体信息
    210   select object_name,object_type,created,last_ddl_time from user_objects
    211   where object_type in ('PACKAGE','PACKAGE BODY');
    212 
    213   --查看包的源代码
    214   select line,text from user_source where name='EMP_MGMT_PKG_OVERLOADING'
    215   and type='PACKAGE';
    216 
    217 
    218   --使用returning into 为记录变量赋值
    219   declare
    220     type t_emp is record(
    221          empno emp.empno%type,
    222          ename emp.ename%type,
    223          sal emp.sal%type
    224     );
    225     emp_info t_emp;
    226     old_sal emp.sal%type;
    227    begin
    228      select sal into old_sal
    229        from emp
    230        where empno=7369;
    231        update emp
    232        set sal=sal*1.1
    233        where empno=7369
    234        returning  empno,ename,sal into emp_info;
    235       dbms_output.put_line(
    236         emp_info.empno||'  '||emp_info.ename ||' '||
    237         old_sal||' '|| emp_info.sal);
    238 
    239      end; 
    240 select sal,ename from emp where empno =7369    
    241 
    242    --在insert语句中使用记录类型
    243    declare
    244      type t_dept_rec is record(
    245           rec_deptno number,
    246           rec_dname varchar2(14),
    247           rec_loc varchar2(13)
    248      );
    249      rec_dept_1 t_dept_rec;
    250      rec_dept_2 dept%rowtype;
    251    begin
    252       rec_dept_1.rec_deptno:=71;
    253       rec_dept_1.rec_dname:='系统部';
    254       rec_dept_1.rec_loc:='上海';
    255       insert into dept values rec_dept_1; 
    256       rec_dept_2.deptno:=72;
    257       rec_dept_2.dname:='开发部';
    258       rec_dept_2.loc:='重庆';
    259       insert into dept values rec_dept_2;
    260   end;     
    261 
    262   select * from dept
    263 
    264 
    265 --在update语句中使用记录类型
    266 declare
    267   rec_dept_2 dept%rowtype;
    268 begin
    269   rec_dept_2.deptno:=20;
    270   rec_dept_2.dname:='系统部';
    271   rec_dept_2.loc:='上海';
    272   update dept set row=rec_dept_2 where deptno=rec_dept_2.deptno;
    273   end;  
    274 
    275     使用记录类型的限制
    276  (1)记录类型不能出现在select语句的选择列表, where子句,group by 子句
    277  或order by子句中
    278  (2)update语句中Row关键字只能出现在set语句之后,并且不能和子查询连用
    279  (3)不能包含其他的变量和值,不能具有嵌套的记录类型,不支持在
    280  execute immediate 语句中使用记录类型.
  • 相关阅读:
    GoLang中面向对象的三大特性
    Go常用功能总结一阶段
    GO语言基础之并发concurrency
    GO语言基础之error
    GO语言基础之reflect反射
    GO语言基础之interface
    GO语言基础之method
    GO语言基础之struct
    GO语言基础map与函数
    GO语言基础条件、跳转、Array和Slice
  • 原文地址:https://www.cnblogs.com/Remedy/p/8747662.html
Copyright © 2011-2022 走看看