Oracle Class6-2. PL/SQL 简介(数据类型,逻辑比较,控制结构,错误处理)
------------------------2013-5-17------------------------
set serveroutput on;
-- Oracle PL/SQL 块
-- 声明部分
declare
lv_Age_num number := 12;
lv_Name_char varchar2(8) default 'AZhu'; --设置默认值--
lv_Sex_char constant varchar2(3) := '男';
-- 执行部分
begin
dbms_output.put_line(lv_Age_num);
dbms_output.put_line(lv_Name_char);
dbms_output.put_line(lv_Sex_char);
dbms_output.put_line('==========');
lv_Age_num := 18;
lv_Name_char := 'ANiu';
dbms_output.put_line(lv_Age_num);
dbms_output.put_line(lv_Name_char);
end;
-- Oracle PL/SQL 块(if then 条件判断)
-- Oracle PL/SQL 块(case 分支判断)
case lv_Age_num
when 10 then
dbms_output.put_line(lv_Name_char || '等于10');
when 18 then
dbms_output.put_line(lv_Name_char || '大于10');
else
dbms_output.put_line(lv_Name_char || '小于10');
end case;
case
when lv_Age_num = 10 then
dbms_output.put_line(lv_Name_char || '等于10');
when lv_Age_num > 10 then
dbms_output.put_line(lv_Name_char || '大于10');
else
dbms_output.put_line(lv_Name_char || '小于10');
end case;
--创建测试表
create table c6(
a int primary key,
b varchar2(10) unique
)
desc c6;
insert into c6 values(1,'Niu1');
select * from c6;
commit;
--批量添加
-- While
declare
lv_A_num number := 2;
begin
while lv_A_num < 5
loop
insert into c6
values
(lv_A_num, 'Niu' || to_char(lv_A_num));
lv_A_num := lv_A_num + 1;
end loop;
-- 提交
commit;
end;
-- For
begin
for i in reverse 11..12 --如果加了reverse,那么表示数字从12,11倒序过来了。--
loop
insert into c6
values
(i, 'Niu' || to_char(i));
end loop;
-- 提交
commit;
end;
--loop exit when方式--
declare
i number := 13;
begin
loop
exit when i = 14;
insert into c6
values
(i, 'Niu' || to_char(i));
i := i +1; --递增算法--
end loop;
-- 提交
commit;
end;
--截断表
truncate table c6;
##过程##
declare
lv_a int; --直接写类型,也可以引用表或视图类型--
lv_b varchar2(10);
begin
select a,b into lv_a,lv_b from c6 where a = 9;
dbms_output.put_line('lv_a:' || lv_a);
dbms_output.put_line('lv_b:' || lv_b);
end;
--record方式--
declare
type lvv is record(
lv_a int,
lv_b varchar2(10)
);
lv lvv;
begin
select a,b into lv from c6 where a = 8; --数据封装的值其实也是一一对应的--
dbms_output.put_line('lv_a:' || lv.lv_a);
dbms_output.put_line('lv_b:' || lv.lv_b);
end;
--record方式+cursor游标方式--
declare
type lvv is record(
lv_a int,
lv_b varchar2(10)
);
lv lvv;
cursor cur is select a,b from c6 where a = 7;
begin
open cur;
fetch cur into lv;
dbms_output.put_line('lv_a:' || lv.lv_a);
dbms_output.put_line('lv_b:' || lv.lv_b);
close cur;
end;
##存储过程##
--record方式+cursor游标方式--
create or replace procedure mypro
as
--declare
type lvv is record(
lv_a int,
lv_b varchar2(10)
);
lv lvv;
cursor cur is select a,b from c6 where a = 7;
begin
open cur;
fetch cur into lv;
dbms_output.put_line('lv_a:' || lv.lv_a);
dbms_output.put_line('lv_b:' || lv.lv_b);
close cur;
end;
#调用#
begin
mypro;
end;
--cursor + record + while--
declare
type lvv is record(
lv_a int,
lv_b varchar2(10)
);
lv lvv;
cursor cur is select a,b from c6 where a > 7; --游标带参数方式,cursor cur (p_a int) is select a,b from c6 where a > p_a;
begin
open cur; --游标带参数方式,open cur(5);
fetch cur into lv;
while cur%found
loop
dbms_output.put_line('lv_a:' || lv.lv_a);
dbms_output.put_line('lv_b:' || lv.lv_b);
fetch cur into lv; --提取下一个
end loop;
close cur;
end;
--cursor + record + while--
declare
cursor cur is select a,b from c6;
begin
-- 以下操作全部自动
-- 打开游标
-- 提取游标
-- 关闭游标
for lv in cur
loop
dbms_output.put_line('lv_a:' || lv.a);
dbms_output.put_line('lv_b:' || lv.b);
end loop;
end;
begin
-- 以下操作全部自动
-- 打开游标
-- 提取游标
-- 关闭游标
for lv in (select a,b from c6) --直接写SQL语句--
loop
dbms_output.put_line('lv_a:' || lv.a);
dbms_output.put_line('lv_b:' || lv.b);
end loop;
end;
###62.sql###
declare
-- 变量名 类型 默认值
name varchar2(8) default 'Aniu';
sex nvarchar2(2) := '男';
-- 常量,定义关键字:constant
Pi constant number(9,8) := 3.14159265;
-- 执行
begin
dbms_output.put_line(Pi);
-- print
dbms_output.put_line(name);
dbms_output.put_line(sex);
--Pi := 4; --会报错,常量不能修改值。
name := 'AZhu';
--dbms_output.put_line(Pi);
dbms_output.put_line(name);
-- 异常处理
-- exception
end;
-- 条件判断 IF
-- 分支判断 CASE(选择器,准确值),(表达式,范围),(比较赋予值)
-- 循环控制 while 条件 loop ... end loop; -- while与loop之间都是没有符号的!!
for i in 5 .. 10 loop ... end loop; for i in reverse 11 .. 15 -- i计数器for递增,不需要手动修改,否则会报错。
loop exit when 条件; end loop;
##case第三个情况##
declare
type lvv is record(
lv_a int,
lv_b varchar2(10)
);
lv lvv;
cursor cur is select a,b from c6;
lv_txt varchar2(18);
begin
open cur;
loop
fetch cur into lv;
exit when cur%notfound;
lv_txt := case lv.lv_a --设置的字段,将值给lv_txt变量--
when '1' then '排第一个'
when '2' then '排第二个'
when '3' then '排第三个'
when '4' then '排第四个'
else '其他'
end;
dbms_output.put_line('lv_txt:' || lv_txt);
end loop;
close cur;
end;
begin
for i in 1..3
loop
dbms_output.put_line(i);
--i := i + 1; -- PLS-00363: 表达式 'I' 不能用作赋值目标
end loop;
end;
-- 语句跳转
begin
dbms_output.put_line('1');
dbms_output.put_line('2');
goto test_row;
dbms_output.put_line('3');
dbms_output.put_line('4');
<<test_row>>
dbms_output.put_line('5');
end;
-- 非法"跳转"
-- 注意:不可跳转至if/while/for/loop等子句
begin
dbms_output.put_line('1');
goto test_row;
dbms_output.put_line('3');
if 1 = 1 then
dbms_output.put_line('4');
<<test_row>>
end if;
dbms_output.put_line('5');
end;
-- 注意:不可从异常处理块中跳转回到PL/SQL块的执行部分
declare
i int;
begin
i := i / 0;
<<test_row>>
exception
when zero_divide then
go_to test_row;
end;
--创建表--
create table c7
(
a int primary key
);
insert into c7 values (1);
select * from c7;
begin
insert into c7 values (1);
exception
when dup_val_on_index then
dbms_output.put_line('错误: 添加重复值!');
end;
-- 捕获自定义异常
-- (1)声明 exception
-- (2)绑定 pragma exception_init(exception, code)
-- (3)捕获
declare
-- 声明异常
Invalid_Number exception;
-- 绑定
pragma exception_init(Invalid_Number, -01722);
begin
insert into c7 values ('ABC');
exception
-- 捕获异常
when Invalid_Number then
dbms_output.put_line('错误: 非法数字值!');
end;
begin
insert into c7 values ('ABC');
exception
-- 捕获异常
when others then -- 其他异常
dbms_output.put_line(sqlcode); -- 异常编号
--dbms_output.put_line(sqlerrmsg); -- 报错:PLS-00201: 必须说明标识符 'SQLERRMSG'
dbms_output.put_line(sqlerrm); -- sqlerrm就对了。
dbms_output.put_line('错误: 未知!');
end;
while cur_titles%found loop end loop;
或
loop exit when cur_titles%notfound end loop;
select trunc(sysdate) from dual;
----------
17-5月 -13
declare
ex_title_test exception;
pragma exception_init( ex_title_test, -01476);
lv_test_num number(4);
lv_errmsg_txt varchar2(80) := 'No any error!';
lv_errnum_txt varchar2(10) := '911';
begin
lv_test_num := 12 / 0;
dbms_output.put_line ( lv_errmsg_txt );
dbms_output.put_line ( lv_errnum_txt );
exception
when ex_title_test then dbms_output.put_line ( '除数不可以为零!' );
lv_errmsg_txt := substr(sqlerrm, 1 , 80);
lv_errnum_txt := sqlcode;
dbms_output.put_line ( lv_errmsg_txt );
dbms_output.put_line ( lv_errnum_txt );
end;
select 60 / 0 from dual;
ORA-01476: 除数为 0
select sqlcode from dual; -- 执行出错
select sqlerrm from dual; -- 执行出错