oracle 学习之 PL/SQL

摘要:
/*PL/SQL:Oracle内部语言SQLServer的是:TSQLProceduralLanguage/SQL是oracle在标准的SQL语言上的扩展,PL/SQL不仅允许嵌入SQL语言,还可以定义变量和常量,允许使用条件语句和循环语句,允许使用例外处理各种错误,这样使得它的功能变得更加的强大.优点:提高应用程序的运行性能,模块化的设计思想,减少网络传输量,提高安全性SQL语言:有两种SQL1
/*
  PL/SQL : Oracle内部语言
  SQLServer的是:TSQL
  Procedural Language/SQL 是oracle在标准的SQL语言上的扩展,PL/SQL不仅允许嵌入SQL语言,还可以
  定义变量和常量,允许使用条件语句和循环语句,允许使用例外处理各种错误,这样使得它的功能变得
  更加的强大.
  
  优点:提高应用程序的运行性能,模块化的设计思想,减少网络传输量,提高安全性
         
  SQL语言:有两种SQL1992/SQL1996  没有循环控制结构
  
  PL/SQL块由三个部分组成:定义部分,执行部分,例外处理部分
  declare
       定义部分 -- 定义常量,变量,游标,例外,复杂数据类型
  begin
       执行部分 -- 要执行的PL/SQL语句和SQL语句
  exception
       例外部分 -- 处理运行的各种错误
  end;
  
  调用过程
  exec 过程名
  call 过程名                
*/

--匿名块


--简单打印一句话

--打开显示
set serveroutput on ;

begin
  dbms_output.put_line('Hello PL/SQL!');
end ;
/


/*
    变量声明的规则
    1 变量名不能够使用保留字
    2 第一个字符必须是字母
    3 变量名最多包含30个字符
    4 不要与数据库的表或者列同名
    5 每一行只能声明一个变量
    
    常用的变量类型
    1 binary_integer : 整数,主要用来计数而不是用来表示字段类型
    2 number: 数字字符
    3 char : 定长字符串
    4 varchar2 : 变长字符串
    5 data : 日期
    6 long : 长字符串最长2GB
    7 boolean : 布尔类型,可以取值true|false和null值
    
*/


--声明变量
declare v_name varchar2(20) ;

declare
	v_temp number(1);
	v_count binary_integer :=0;
	v_sal number(7,2) :=4000.00;
	v_date date :=sysdate ;
	v_pi constant number(3,2) :=3.14;
	v_valid boolean :=false;
	v_name varchar2(20) not null :='hello plsql' ;
begin 
	dbms_output.put_line('v_temp value :'||v_temp);
end;

--根据表中字段类型声明变量类型的
declare 
	v_empno number(4);
	v_empno2 emp.empno%type;
	v_empno3 v_empno2%type;
begin
	dbms_output.put_line('test');
end;

/*
  复杂变量
  Table变量类型 : 集合  (表示集合时要自己定义的一个新的数据类型)
  Record变量类型 : 类 (代表实体,一条记录)
*/
--定义Table变量类型
--Table 变量类型(数组)
declare
	type type_newname is table of emp.empno%type index by binary_integer; --声明一个数组类型 index by binary_integer 指系统创建一个主键索引,以引用记录表变量中的特定的行。
		v_empnos type_newname ;  --用数组类型定义变量
begin
	v_empnos(0) :=7369;
	v_empnos(2) :=7839;
	v_empnos(-1):=9999;
	dbms_output.put_line(v_empnos(-1));
end;

--Record变量类型
declare
	type type_record_dept is record
		(
			deptno dept.deptno%type,
			dname dept.dname%type,
			loc dept.loc%type
		);
	v_temp type_record_dept ;
begin 
	v_temp.deptno :=50 ;
	v_temp.dname  :='aaa';
	v_temp.loc    :='bj';
	dbms_output.put_line(v_temp.deptno || ' ' || v_temp.dname);
end;

--使用%rowtype 声明record变量
declare
	v_temp dept%rowtype;   --直接用一张表的行来定义record,表结构变化时record也在变
begin
	v_temp.deptno :=50;
	v_temp.dname  :='aaa';
	v_temp.loc    :='bj';
	dbms_output.put_line(v_temp.deptno||' '||v_temp.dname);
end ;

/*
    PL/SQL中的SQL语句
    select 语句返回有且只有一条记录
*/
--select语句
declare
	v_ename emp.ename%type;
	v_sal emp.sal%type;
begin
	select ename,sal into v_ename,v_sal from emp where empno =7369;
	dbms_output.put_line(v_ename || ' '||v_sal);
end;

declare
	v_temp emp%rowtype;
begin
	select * into v_emp from emp where empno=7369;
	dbms_output.put_line(v_temp.ename);
end;


--insert 语句
declare
	v_deptno dept.deptno%type :=10;
	v_dname dept.dname%type :='aaa';
	v_loc dept.loc%type :='beijing' ;
begin
	insert into dept2 values(v_deptno,v_dname,v_loc);
	commit;
end;

--update语句
declare
	v_deptno emp2.deptno%type :=10 ;
	v_count number;
begin
	update emp2 set sal = sal/2 where deptno = v_deptno ;
	--select deptno into v_deptno from emp2 where empno = 7369;
	--select count(*) into v_count from emp2 ;
	dbms_output.put_line(sql%rowcount||'条记被影响');
	commit ;
end;

--DDL语句
begin
  execute immediate 'create table t_temp(nnn varchar2(20) default "aaa")' ;
end ;

--语句块
declare
	v_name varchar2(20);
begin
	v_name := 'jack' ;
	dbms_output.put_line(v_name);
end;

--带异常捕获的语句块
declare
	v_num number :=0 ;
begin
	v_num :=2/v_num ;
	dbms_output.put_line(v_num);
exception
	when others then
		dbms_output.put_line('error');
end;

--分支语句
--if 取出7369的薪水,如果<1200,则输出'low',如果<2000则输出'middle',否则'high'
declare 
	v_sal emp.sal%type;
begin
	select sal into v_sal from emp where empno=7369;
	if(v_sal<1200) then
		dbms_output.put_line('low');
	elsif(v_sal<2000) then
		dbms_output.put_line('middle');
	else 
		dbms_output.put_line('high');
	end if;
end;

--循环  (相当于do...while)
declare
	i binary_integer :=1;
begin
	loop 
		dbms_output.put_line(i);
			i := i+1 ;
			exit when(i>=11);
	end loop;
end;

declare
	j binary_integer :=1;
begin
	while j<11 loop
		dbms_output.put_line(j);
			j := j+1 ;
	end loop ;
end;

begin
	for k in 1..10 loop 
		dbms_output.put_line(k);
	end loop;
	for k in reverse 1..10 loop 
		dbms_output.put_line(k);
	end loop;
end;

--错误处理
declare
	v_temp number(4);
begin
	select empno into v_temp from emp where deptno =10 ;
exception
	when too_many_rows then
		dbms_output.put_line('太多记录了');
	when others then
		dbms_output.put_line('error');
end;

declare
	v_temp number(4);
begin
	select empno into v_temp from emp where empno=2222;
exception
	when no_data_found then
		dbms_output.put_line('没数据');
end;

--错误记录
create table errorlog
(
	id number primary key,
	errcode number,
	errmsg varchar2(1024),
	errdate date
);

create sequence seq_errorlog_id start with 1 increment by 1;

declare
	v_deptno dept.deptno%type :=10 ;
	v_errcode number ;
	v_errmsg varchar2(1024) ;
begin
	delete from dept where deptno=v_deptno;
	commit;
exception
	when others then
		rollback;
		v_errcode :=SQLCODE;
		v_errmsg  :=SQLERRM;
		insert into errorlog values(seq_errorlog_id.nextval,v_errcode,v_errmsg,sysdate);
		commit;
end;

select * from errorlog;

触发器

/*
  触发器 trigger
	触发器必须依附于表才能起作用
*/

--创建日志表 emp_log,用于记录对表emp的所有操作日志
create table emp_log
(
	uname varchar2(20),
	action varchar2(10),
	atime date
);

--创建触发器
/*
	触发条件:insert|delete|update 对某张表做插入|删除|更新的操作
	触发时间:after|before 操作之后|操作之前
	触发行:each row 操作影响一行触发一次,不写表求一次操作触发一次
*/
create or replace trigger trig
	after insert or delete or update on emp for each row
begin
	if inserting then
		insert into emp_log(uname,action,atime) values(USER,'insert',sysdate);
	elsif updating then
		insert into emp_log(uname,action,atime) values(USER,'update',sysdate);
	elsif deleting then
		insert into emp_log(uname,action,atime) values(USER,'delete',sysdate);
	end if ;
end;
/

--触发
update emp set sal=sal*2 where deptno=30;
delete from emp where empno = 7369 ;


--查看日志表
select * from emp_log;

--? : 有外键关系时,主表中的主键存在外表的引用关系,因此不能随意更新,但可以用触发器解决这个问题
    --如: update dept set deptno=99 where deptno=10

--删除触发器
drop trigger trig;

create or replace trigger trig
	after update on dept for each row
begin
	update emp set deptno = :NEW.deptno where deptno = :OLD.deptno ;
end;
/
/*
	通常一条update语句会产生新旧两个状态 :NEW代表新状态 :OLD代表旧状态
*/
update dept set deptno=99 where deptno=10;

免责声明:文章转载自《oracle 学习之 PL/SQL》仅用于学习参考。如对内容有疑问,请及时联系本站处理。

上篇201601读书分享——《微创新》jquery 多级联动下拉列表含(数据模型)下篇

宿迁高防,2C2G15M,22元/月;香港BGP,2C5G5M,25元/月 雨云优惠码:MjYwNzM=

相关文章

SQL 语句解析

查询语句 1.基础查询: SELECT * FROM 表 解析:此语句会将表中所有的字段查询出来,SQL执行的顺序:FROM 表 (找到表)=>SELECT *  (查询所有字段*代表所有字段) SELECT ID,NAME FROM 表 解析:此语句会将表中所有的字段查询出来,SQL执行的顺序:FROM 表 (找到表)=>SELECT  ...

[心得体会]mysql复习

1. 进入企业需要注意的事情(1) 查看测试服和本地的mysql版本是否一致(2) 确认sql_mode是否和线上版本一致 showVARIABLESLIKE'sql_mode'; (3) mysql sql_mode 常用设置详解: ONLY_FULL_GROUP_BY: 对于GROUP BY聚合操作,如果在SELECT中的列,没有在GROUP BY...

Oracle查询用户权限

Oracle查询用户权限-- 确定角色的权限select * from role_tab_privs ; 包含了授予角色的对象权限select * from role_role_privs ; 包含了授予另一角色的角色select * from role_sys_privs ; 包含了授予角色的系统权限-- 确定用户帐户所授予的权限select * fro...

06 django视图层

视图层   视图就是一个函数,请求过来后要做什么事情都在这个函数里,也就是具体处理请求的功能。   熟练掌握两个视图层对象:请求对象(request)和响应对象(HttpResponse)。 HttpRequest对象 1 from django.shortcuts import render,redirect,HttpResponse 2 from...

oracle中Blob和Clob类型的区别

一、oracle中Blob和Clob类型的区别BLOB和CLOB都是大字段类型,BLOB是按二进制来存储的,而CLOB是可以直接存储文字的。其实两个是可以互换的的,或者可以直接用LOB字段代替这两个。但是为了更好的管理ORACLE数据库,通常像图片、文件、音乐等信息就用BLOB字段来存储,先将文件转为二进制再存储进去。而像文章或者是较长的文字,就用CLOB...

Makefile写法入门心得

Makefile的写法入门心得   Makefile的出现使得编译过程极大地自动化了,省去了很多人工工作,非常方便。这里,小结一下写Makefile的一点小心得。嗯,对了,差点忘了一件事,同一个Makefile在不同的内核版本和Linux发行版本中不一定能发挥一样的作用,别人的Makefile可不见得就适用于自己的机器。 我先简单说一下我自己的机器: Ub...