1.什么是存储过程:预先经过编译并存储在数据库中的一段sql语句的集合。

2.使用存储过程的优点(1)已经编译过,调用时无需编译,提高工作效率。

           (2)存放在数据库中,客户端通过存储过程的名字直接调用,减少网络流量,加快系统执行速度。

           (3)减少sql注入,且有权限的其情况下才能调用存储过程,提高安全性。

           (4)和编程相分离,业务发生变化,需要修改数据库的地方无需修改代码,直接修改存储过程,较方便。

3.使用存储过程的缺点占用服务器较多资源,对服务器造成压力。

4.什么时候使用存储过程:业务逻辑复杂的时候。

5.怎么写存储过程:

  (1)准备工作,创建表,插入数据,这里我用的是sqlplus

SQL> create table student(
  2  id varchar2(11) primary key,
  3  name varchar2(32),
  4  age integer
  5  );

Table created.
SQL> insert into student values('1','小明',10);

SQL> insert into student values('2','小红',11);

SQL> insert into student values('3','小蓝',12);

  (2)-----------------------第一个简单的不带参数的存储过程-----------------------------------------------------

SQL> create or replace procedure studentcount
  2  as student_count number(10);
  3  begin
  4  select count(1) into student_count from student;
  5  dbms_output.put_line('总人数:'||student_count);
  6  end;
  7  /

create or replace :创建或替换,有的时候你不知道你要创建的存储过程存不存在可以用create or replace,不然会报错

procedure:存储过程关键字

as:用于定义变量的一个块,这里定义你要使用的变量

begin:存储过程开始,里面执行你的逻辑

dbms_output.put_line:用在begin..end之间,控制台输出   '||'是oracle用于字符串连接,如果没有打印出来,执行set serveroutput on;再调用存储过程就能打印出来

end:存储过程结束

调用方式(1):

SQL> set serveroutput on;
SQL> begin
  2  studentcount();
  3  end;
  4  /
总人数:3

PL/SQL procedure successfully completed.

调用方式(2):

SQL> exec studentcount();
总人数:3

PL/SQL procedure successfully completed.

(3)----------------带参数的存储过程------------------------------------------------------------------------------------ 

 create or replace procedure studentinfo(
 id in varchar2,
 name varchar2,
 studentcount out varchar2
 )
 as
 begin
 select count(1) into studentcount from student where id=id and name=name;
 Dbms_Output.put_line('id为:'||id||'姓名为'||name||'的学生有'||studentcount||'');
 end;

参数说明:参数有3种类型,in,out,in out ,in是作为输入参数,当参数没有指定类型的时候就是in类型,out是输出参数,in out 既可以作为输入参数也可以作为输出参数。这里参数是不需要指明宽度的,in的宽度由外部调用的时候决定,out由存储过程内部决定。in类型的参数可以有默认值,out类型的参数不能有默认值,不然会报错。

调用:  

SQL> set serveroutput on;
SQL> declare scount varchar2(1);
  2  begin
  3  studentinfo('1','小明',scount);
  4  end;
  5  /
id为:1姓名为小明的学生有3位

PL/SQL procedure successfully completed.

 

发现怎么有3位不对,把定义的id,name换个名字就好了,那么这里发现sql中where查询条件不能带上表的一样的字段名。

有的时候你不知道参数是什么类型,或者表里面字段类型会变,可以用%type来表示

 

create or replace procedure studentinfo2(
 sid in student.id%type, --表示和student表里id的字段类型
 sname  student.name%type,--表示和student表里name的字段类型
 studentcount out varchar2
 )
 as
 begin
 select count(1) into studentcount from student where id=sid and name=sname;
 Dbms_Output.put_line('id为:'||sid||'姓名为'||sname||'的学生有'||studentcount||'');
 end;

 ***********返回一行数据的存储过程用%rowtype 

create or replace procedure studentinfo3(
 sid in student.id%type,
 sname  student.name%type,
 studentinfos out student%rowtype  --匹配student表里的一行数据
 )
 as
 begin
 select * into studentinfos from student where id=sid and name=sname;
 Dbms_Output.put_line('id为'||studentinfos.id||'姓名为:'||studentinfos.name);
 end;

***********返回结果集(可以用游标)

 create or replace procedure studentinfo4
 (s_info out sys_refcursor)
 as
begin
   open s_info for 'select * from student';
  
end;

调用:

SQL> declare
  2    cur1   SYS_REFCURSOR;
  3    i      student%rowtype;
  4  begin
  5   studentinfo4(cur1);
  6    loop
  7      fetch cur1 into i;
  8      exit when cur1%notfound;--检索到没有数据就退出循环
  9      dbms_output.put_line('----------------:' || i.id);
 10    end loop;
 11    close cur1;
 12  end;
 13  /
----------------:1
----------------:2
----------------:3

PL/SQL procedure successfully completed.

查看自己写的存储过程:

select text from user_source where name=upper('你要查询的存储过程名称') and type=upper('procedure'); 

user_source 是存放oracle源代码的一个字典。

删除存储过程:

SQL> drop procedure studentinfo4;

这是目前本人对于oracle学习的一个总结,希望对你们有帮助,不对的地方请望指出,谢谢!

posted on 2017-05-27 16:57  wjdxw  阅读(139)  评论(0编辑  收藏  举报