----for循环---------------------------------------
FOR ... in ... LOOP
END LOOP;
BEGIN
FOR i IN 1..10 LOOP
dbms_output.put_line(i);
END LOOP;
END;
问题 1 到 50 ?
3到40 ?
----while循环----------------------------------
WHILE ... LOOP
END LOOP;
declare
n number(3) :=10;
begin
WHILE n>=0 LOOP
dbms_output.put_line(n);
n:=n-1;
END LOOP;
end;
/
问题 : 1 2 3 到 50
2 4 6 8 10
15 16 17 18 19 。。。。 30
length('abc') --获取字符长度
select substr('abc',2,1) from dual;--从第2个字符开始截取1个
--使用 while 循环 将你的名字倒序输出
declare
str varchar2(50):='包玉坤';
len number(5);
c char(2);
begin
len := length(str);
while len>0 loop
c := substr(str,len,1);
dbms_output.put_line(c);
len := len-1;
end loop;
end;
SQL> declare
2 str varchar2(50):='包玉坤';
3 len number(5);//计数
4 c char(2);//
5 begin
6 len := length(str);//用length计算字符串长度=3
7 while len>0 loop//条件:len>0
8 c := substr(str,len,1);//截取字符串substr(‘字符’,‘从几位开始’,‘取几位’)=(‘暴雨坤’,’3‘,’1‘)坤
9 dbms_output.put_line(c);//输出c
10 len := len-1;//每循环一次减一
11 end loop;
12 end;
13 /
declare
str varchar2(50):='春天不洗澡处处蚊子咬请洒敌敌畏蚊子全死了';
len number(5);
c char(2);
begin
len := length(str);
while len>0 loop
c := substr(str,len,1);
dbms_output.put_line(c);
len := len-1;
end loop;
end;
-------------------------------------------------
触发器
create table Disney
(
id number primary key,
data varchar2(10)
);
create sequence id_seq;
create or replace trigger bifer_disney_id_pk
beFORe insert
on Disney
FOR each row
begin
select id_seq.nextval into :new.id FROM dual;
end;
/
insert into Disney(data) VALUES('tom');
insert into Disney(id,data) VALUES('6','jerry');
select * from Disney;
----------------------------------------------
电话记录表PHONE_DETAIL
--主键ID
--电话号码PHONE_NO
--记录时间CREATE_TIME (使用当前系统时间)
--通话时长(分钟)DURATION
--通话资费类型COST_ID
--通话费用COST (单价*时长)
create table phone_detail(
id number(11) primary key,
phone_no varchar2(20),
create_time date,
duration number(10),
cost_id number(11),
cost number(11,2)
);
create sequence phone_seq;
服务资费表PHONE_COST
--资费类型COST_ID
--资费名COST_NAME
--单价(元/分钟)COST_PRICE
--number(5,2)五位数,两位小数
create table phone_cost(
cost_id number(11) primary key,
cost_name varchar2(20),
cost_price number(5,2)
);
insert into phone_cost
values (1,'A资费',1.5);
insert into phone_cost
values (2,'B资费',0.5);
insert into phone_cost
values (3,'C资费',0.3);
需求:当向PHONE_DETAIL表中插入记录
时,采用触发器自动计算出通话费用
COST字段值写入。
insert into PHONE_DETAIL
(id,phone_no,duration,
cost_id,create_time)
values (phone_seq.nextval,
'13111111112',8,3,sysdate);
上述insert执行后,自动计算出cost值写入
=====触发器=======
create or replace trigger cost_trigger
before insert on PHONE_DETAIL
for each row
declare
v_price number(7,2) :=0;
v_cost number(7,2) :=0;
begin
select cost_price into v_price
from phone_cost
where cost_id=:NEW.cost_id;
v_cost := v_price*:NEW.duration;
:NEW.cost := v_cost;
end;
/
//覆盖掉原来记录new
------------------------------------
4)触发器
触发器不用显式调用,是由一些
数据库操作自动触发。例如insert,
update,delete等动作触发,也可以
由登录或登出等事件触发。
触发器分类:
*a.DML触发器
由DML语句操作触发.DML触发器
又分为语句级触发器和行级触发器。
语句级:对表执行insert,delete,
update时触发调用一次。
行级:每行记录调用一次触发器功能
行级触发器可以获取当前操作的记录
b.系统触发器
由系统事件触发,比如登录,登出
DML触发器创建格式:
create or replace trigger 触发器名
before|after ?事件类型 on 表
declare
--定义区
begin
--主处理区
exception
--异常处理区
end;
/
--查7499的津贴
declare
v_name varchar2(10);
v_sal number(7,2);
begin
select ename,sal
into v_name,v_sal
from emp
where empno=7499;
dbms_output.put_line('姓名:'||v_name);
dbms_output.put_line('工资:'||v_sal);
end;
/
--7499的入职日期
declare
v_name varchar2(10);
v_sal number(7,2);
v_job emp.job%type ;
v_HIREDATE emp.hiredate%type;
begin
select ename,sal,hiredate,job
into v_name,v_sal,v_HIREDATE,v_job
from emp
where empno=&n;
dbms_output.put_line('职员姓名:'||v_name);
dbms_output.put_line('工资:'||v_sal);
dbms_output.put_line('入职日期:'||v_HIREDATE);
dbms_output.put_line('工作:'||v_job);
end;
游标
什么时候用?
用于提取表中多行记录
单行使用select ... into...
怎么定义?
CURSOR 名称 IS select语句;
怎么用?
OPEN 游标名;
fetch 游标名 into 变量
CLOSE 游标名;
利用游标名%NOTFOUND结束循环.
fetch 游标名 into 变量
exit when 游标名%NOTFOUND;
--数据处理
declare
CURSOR c_emp_cursor IS
select ename,sal from emp;
v_name varchar2(10);
v_sal number(7,2);
begin
OPEN c_emp_cursor;
loop
FETCH c_emp_cursor
INTO v_name,v_sal;
exit when c_emp_cursor%NOTFOUND;
dbms_output.put_line(v_name||v_sal);
end loop;
CLOSE c_emp_cursor;
end;
-------------作业p179---------------------
--编写pl/sql块,根据输入的部门编号统计部门内的员工总人数
declare
n_deptno number;
n_total number;
no_dept exception;
begin
n_deptno:=&n;
select count(deptno) into n_total
from emp where deptno=n_deptno;
if n_total=0 then
raise no_dept;
else
dbms_output.put_line(n_deptno||'部门的总人数为'||n_total);
end if;
exception
when no_dept then dbms_output.put_line('此部门不存在');
end;
--if条件分支控制语句。工作时间满15年增加1000元薪水,10-15增加500元,少于10增加200元
declare
n_hire number(6,2);
n_empno number;
begin
n_empno:=&n;
select months_between(sysdate,hiredate)into n_hire from emp where empno=n_empno;
if n_hire>=360 then
Update emp set sal=sal+1000 where empno=n_empno;
elsif n_hire>=240 then
Update emp set sal= sal+500 where empno=n_empno;
else Update emp set sal=sal+300 where empno=n_empno;
end if ;
end;
set serveroutput on
--用for循环打印三角形
begin
for i in 1..10
loop
for j in 1..i
loop
dbms_output.put('*');
end loop;
dbms_output.put_line('');
end loop;
end;
--附加1:
declare --定义变量部门,总人数,
n_deptno number;
n_total number;
no_dept exception;
begin
n_deptno:=&n;
select count(deptno) into n_total
from emp where deptno=n_deptno;
if n_total=0 then
raise no_dept;
else
dbms_output.put_line(n_deptno||'部门的总人数为'||n_total);
end if;
exception
when no_dept then dbms_output.put_line('此部门不存在');
end;
--附加2:
declare
n_deptno number;
begin
n_deptno:=&n;
if n_deptno=10 then
Update emp set sal=sal+100 where deptno=n_deptno;
elsif n_deptno=20 then
Update emp set sal= sal+50 where deptno=n_deptno;
elsif n_deptno=20 then
Update emp set sal=sal+30 where deptno=n_deptno;
end if ;
end;
--附加3:
decale
a_num int:=1;
begin
for i in 1..6 loop
a_num :=a_num*i;
end loop;
dbms_output.put_line(a_num);
end;