ORACEL plsql学习笔记

1  什么是plsql?

  PL/SQL(Procedure Language/SQL)是 Oracle 对 sql 语言的过程化扩展,指 在 SQL 命令语言中增加了过程处理语句(如分支、循环等),使 SQL 语言具有过程处理能力。把 SQL 语言的数据操纵能力与过程语言的数据处理能力结合起来,使得 PLSQL 面向过程但比过程语言简单、高效、灵活和实用.

2 plsql语法

2.1 变量声明与赋值

--变量声明与赋值
declare
  v_price number(10,2);--单价
  v_usenum number;--水费字数
  v_usenum2 number(10,2);--吨数
  v_money number(10,2);--金额
begin
  v_price:=2.45;--单价赋值
  v_usenum:=9213;--水费字数
  v_usenum2:=round( v_usenum/1000,2);--吨数
  v_money:=v_price*v_usenum2;--金额
  
  DBMS_OUTPUT.put_line('金额:'||v_money);

end;

2.2 --select  列名 into 变量名

--select  列名 into 变量名

declare
  v_price number(10,2);--单价
  v_usenum number;--水费字数
  v_usenum2 number(10,2);--吨数
  v_money number(10,2);--金额
  v_num0 number;--上月水表数
  v_num1 number;--本月水表数
begin
  v_price:=2.45;--单价赋值
  --v_usenum:=9213;--水费字数
  select usenum,num0,num1 into v_usenum,v_num0,v_num1 from t_account 
  where year='2012' and month='01' and owneruuid=1;
  
  v_usenum2:=round( v_usenum/1000,2);--吨数
  v_money:=v_price*v_usenum2;--金额
  
  DBMS_OUTPUT.put_line('字数:'||v_usenum||'金额:'||v_money);

end;

2.3 --属性类型 (引用型  表名.列名%type)

--属性类型 (引用型  表名.列名%type)
declare
  v_price number(10,2);--单价
  v_usenum t_account.usenum%type;--水费字数
  v_usenum2 number(10,2);--吨数
  v_money number(10,2);--金额
  v_num0 t_account.num0%type;--上月水表数
  v_num1 t_account.num1%type;--本月水表数
begin
  v_price:=2.45;--单价赋值
  --从数据库中提取
  select usenum,num0,num1 into v_usenum,v_num0,v_num1 from t_account 
  where year='2012' and month='01' and owneruuid=1;
  
  v_usenum2:=round( v_usenum/1000,2);--吨数
  v_money:=v_price*v_usenum2;--金额
  
  DBMS_OUTPUT.put_line('字数:'||v_usenum||'金额:'||v_money);

end;

2.4 --属性类型 (记录型  表名%rowtype  )

--属性类型 (记录型  表名%rowtype  )
declare
  v_price number(10,2);--单价
 
  v_usenum2 number(10,2);--吨数
  v_money number(10,2);--金额
  v_account t_account%rowtype;--台账行记录类型 
begin
  v_price:=2.45;--单价赋值
  --从数据库中提取
  select * into v_account from t_account 
  where year='2012' and month='01' and owneruuid=1;
  
  v_usenum2:=round( v_account.usenum/1000,2);--吨数
  v_money:=v_price*v_usenum2;--金额
  
  DBMS_OUTPUT.put_line('字数:'||v_account.usenum||'金额:'||v_money);

end;

2.5  --异常处理1

--异常处理1
declare
  v_price number(10,2);--单价
 
  v_usenum2 number(10,2);--吨数
  v_money number(10,2);--金额
  v_account t_account%rowtype;--台账行记录类型 
begin
  v_price:=2.45;--单价赋值
  --从数据库中提取
  select * into v_account from t_account 
  where year='2012' and month='01' and owneruuid=200;
  
  v_usenum2:=round( v_account.usenum/1000,2);--吨数
  v_money:=v_price*v_usenum2;--金额
  
  DBMS_OUTPUT.put_line('字数:'||v_account.usenum||'金额:'||v_money);

exception
  when no_data_found  then
    DBMS_OUTPUT.put_line('没有找到账务数据');
end;

2.6 --异常处理2

--异常处理2
declare
  v_price number(10,2);--单价
 
  v_usenum2 number(10,2);--吨数
  v_money number(10,2);--金额
  v_account t_account%rowtype;--台账行记录类型 
begin
  v_price:=2.45;--单价赋值
  --从数据库中提取
  select * into v_account from t_account 
  where year='2012' and month='01' ;
  
  v_usenum2:=round( v_account.usenum/1000,2);--吨数
  v_money:=v_price*v_usenum2;--金额
  
  DBMS_OUTPUT.put_line('字数:'||v_account.usenum||'金额:'||v_money);

exception
  when no_data_found  then
    DBMS_OUTPUT.put_line('没有找到账务数据');
  when too_many_rows then
    DBMS_OUTPUT.put_line('返回多行账务数据');
end;

2.7 --条件判断

--条件判断
declare
  v_price1 number(10,2);--单价
  v_price2 number(10,2);--单价
  v_price3 number(10,2);--单价
 
  v_usenum2 number(10,2);--吨数
  v_money number(10,2);--金额
  v_account t_account%rowtype;--台账行记录类型 
begin
  v_price1:=2.45;--单价赋值(5吨以下)
  v_price2:=3.45;--单价赋值 (5-10吨)
  v_price3:=4.45;--单价赋值 (超过10吨)
  
  --从数据库中提取
  select * into v_account from t_account 
  where year='2012' and month='01' and owneruuid=1 ;
  
  v_usenum2:=round( v_account.usenum/1000,2);--吨数
  
  
  --v_money:=v_price*v_usenum2;--金额
  
  --阶梯水费计算
  
  if v_usenum2<=5 then 
    v_money:=v_price1*v_usenum2;
  elsif v_usenum2>5 and v_usenum2<=10  then 
    v_money:=v_price1*5+ v_price2*( v_usenum2-5 );
  else
    v_money:=v_price1*5+ v_price2*5 +v_price3*(v_usenum2-10);
  end if;
  
  
  DBMS_OUTPUT.put_line('字数:'||v_account.usenum||'金额:'||v_money);

exception
  when no_data_found  then
    DBMS_OUTPUT.put_line('没有找到账务数据');
  when too_many_rows then
    DBMS_OUTPUT.put_line('返回多行账务数据');
end;

2.8 --无条件循环:1 到100

--无条件循环:1 到100

declare
  v_num number;  
begin
  v_num:=1;
  loop
    dbms_output.put_line(v_num);
    v_num:=v_num+1;  
    
    exit when v_num>100;
    
  end loop;
end ;

2.9 --有条件循环:1 到100

--有条件循环:1 到100
declare
  v_num number;
begin
  v_num:=1;
  
  while  v_num<=100
  loop
     dbms_output.put_line(v_num);
     v_num:=v_num+1;  
  
  end loop; 
end;

2.10 --for循环

--for循环
begin
  
  for v_num in  1 .. 100  
  loop
    dbms_output.put_line(v_num);
  end loop;

end;

2.11 --游标

--游标 

select * from t_pricetable where ownertypeid=1
---------
declare
  cursor cur_pricetable is select * from t_pricetable where ownertypeid=1;--声明游标
  v_pricetable t_pricetable%rowtype;
begin
  
  open cur_pricetable;--打开游标
  loop
    fetch cur_pricetable into v_pricetable;--提取游标
    exit when cur_pricetable%notfound;--如果游标到底端,循环结束
    
    DBMS_OUTPUT.put_line('价格:'||v_pricetable.price||'吨数:'
          ||v_pricetable.minnum||'-'||v_pricetable.maxnum);  
    
  end loop;
  
  close cur_pricetable;--关闭游标
end;

2.12 --带参数的游标

--带参数的游标
declare
  cursor cur_pricetable(v_type number) 
         is select * from t_pricetable where ownertypeid=v_type;--声明游标
  v_pricetable t_pricetable%rowtype;
begin
  
  open cur_pricetable(2);--打开游标时指定参数值
  loop
    fetch cur_pricetable into v_pricetable;--提取游标
    exit when cur_pricetable%notfound;--如果游标到底端,循环结束
    
    DBMS_OUTPUT.put_line('价格:'||v_pricetable.price||'吨数:'
          ||v_pricetable.minnum||'-'||v_pricetable.maxnum);  
    
  end loop;
  
  close cur_pricetable;--关闭游标
end;

2.13  --for循环 带参数的游标

--for循环 带参数的游标
declare
  cursor cur_pricetable(v_type number) 
         is select * from t_pricetable where ownertypeid=v_type;--声明游标
  --v_pricetable t_pricetable%rowtype;
begin
  
  for v_pricetable in cur_pricetable(3)
  loop
    DBMS_OUTPUT.put_line('价格:'||v_pricetable.price||'吨数:'
          ||v_pricetable.minnum||'-'||v_pricetable.maxnum); 
  end loop;  
 
end;

2.14 --存储函数创建

--存储函数创建
create or replace function fn_getaddress
(v_id number)
return varchar2
is
  v_name varchar2(30);
begin
  --查询地址表
  select name into v_name from t_address where id=v_id;
  return v_name;
end; 

--存储函数测试
select fn_getaddress(3) from dual;

--存储函数应用
select id,name,fn_getaddress(addressid) from t_owners;

2.15  创建不带传出参数的存储过程

create sequence seq_owners start with 11;--业主序列

--创建不带传出参数的存储过程
create or replace procedure pro_owners_add 
(
v_name varchar2,--名称
v_addressid number,--地址编号
v_housenumber varchar2,--门牌号
v_watermeter varchar2,--水表号
v_ownertypeid number--业主类型
)
is

begin
  insert into t_owners 
         values( seq_owners.nextval,v_name,v_addressid,v_housenumber ,v_watermeter,sysdate,v_ownertypeid ); 
  commit;
end;

--调用不带传出参数的存储过程
call pro_owners_add( '马大哈',2,'22333','66777',1 );

begin
  pro_owners_add( '马小哈',2,'22333','223344',1 );
end;

2.16 --创建带传出参数的存储过程

--创建带传出参数的存储过程
create or replace procedure pro_owners_add 
(
v_name varchar2,--名称
v_addressid number,--地址编号
v_housenumber varchar2,--门牌号
v_watermeter varchar2,--水表号
v_ownertypeid number,--业主类型
v_id out number
)
is

begin
  --对传出参数赋值
  select seq_owners.nextval into v_id from dual;
  --新增业主
  insert into t_owners 
         values( v_id,v_name,v_addressid,v_housenumber ,v_watermeter,sysdate,v_ownertypeid ); 
  commit;
  
end;

--调用传出参数的存储过程
declare
  v_id number;
begin
  pro_owners_add( '马二哈',2,'22333','2233666',1,v_id );
  dbms_output.put_line(v_id);  
end;

2.17 --前置触发器

create or replace trigger tri_account_num1
before
update of num1
on t_account
for each row
declare

begin
  --通过伪记录变量修改usenum字段的值
  :new.usenum:= :new.num1-:new.num0;
    
end;

2.18 --后置触发器

--后置触发器
--创建日志表,记录业主名称修改前和修改后的名称 
create table t_owners_log(
updatetime date,
ownerid number,
oldname varchar2(30),
newname varchar2(30)
);

create or replace trigger tri_owners_log
after
update of name
on t_owners
for each row
declare

begin
  --向日志表插入记录
  insert into t_owners_log values(sysdate,:new.id,:old.name,:new.name);

end;


update t_owners set name='林玲玲' where id=4;

猜你喜欢

转载自www.cnblogs.com/pierceming/p/10311862.html