整体结构
1 2 3 4 5 6 7 8 9 10 11 12 13 14
| set serveroutput on declare out_text1 varchar2(50); begin declare out_text2 varchar2(50); begin out_text2:='内层程序块'; dbms_output.put_line(out_text2); end; out_text1:='外层程序块'; dbms_output.put_line(out_text1); end; /
|
标识符
- 以字母开头
- 不区分大小写
- 不能超过30单位长度
- 不能有‘-’和空格
- 不能是SQL关键字
在SQL*Plus查看SQL关键字
标量和变量
量名 |
备注 |
NUMBER(p,s) |
p为数据长度,s为小数个数,皆为可选 |
PLS_INTEGER |
类似,-2^31~2^31,速度快,CUP利用率高,溢出触发异常 |
BINARY_INTEGER |
类似pls_number,溢出赋值给number且未超出number范围时,不会异常 |
POSITIVE |
正整数 |
NATURAL |
自然数 |
DATE |
日期型 |
BOOLEAN |
布尔值 |
CHAR |
字符型 |
VARCHAR |
可变长度字符串 |
VARCHAR2 |
Oracle自定义的一种类型,是作为以后升级后的兼容后门。varchar就不一定兼容了。 |
常量
1
| PI CONSTANT NUMBER(9) := 3.1415926;
|
NUMBER详解——》传送门
强制转换到字符型
混搭SQL语句
1 2 3 4 5 6 7 8 9 10
| set serveroutput on declare a number(4); begin select count(编号) into a from Student; dbms_output.put_line(a); end; /
|
TYPE和ROWTYPE类型的变量
TYPE
先去查询目标表的列属性,然后将该属性类型设置给变量。
1 2 3 4 5 6 7 8 9 10
| set serveroutput on declare a Student.sname%TYPE; begin select sname into a from Student; dbms_output.put_line(a); end; /
|
ROWTYPE
形成一个RECODE,类似与c++的struct,其中每一个值都是TYPE类型。
1 2 3 4 5 6 7 8 9 10 11 12 13
| set serveroutput on declare a Student%ROWTYPE; begin select * into a from Student; dbms_output.put_line(a.sid); dbms_output.put_line(a.sname); dbms_output.put_line(a.ssex); dbms_output.put_line(a.sage); end; /
|
复合变量
记录类型
语法
1 2 3 4 5
| TYPE RECORD_NAME IS RECORD( feildname1 data_type [not null] [:=defualt_value], ··· feildnamen data_type [not null] [:=defualt_value], )
|
样例
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
| set serveroutput on declare TYPE Sturecord IS RECORD( ID VARCHAR2(20) NAME VARCHAR2(20) SEX CHAR AGE INTEGER ); a Sturecord; begin select sid,sname,ssex,sage into a from Student where sid=1; dbms_output.put_line(a.ID); dbms_output.put_line(a.NAME); dbms_output.put_line(a.SEX); dbms_output.put_line(a.AGE); end; /
|
注意
- select语句是按顺序逐个查询的,所以select后列的顺序要与record的中类型的顺序要匹配
- 假如record_a与record_b除了名字之外完全一样,a类型的值也不能赋给b类型。
记录表类型
- 记录类型一个变量只能存一行信息,记录表类型可以存多行信息。
- 不会存储入数据库,只在内存中生存。
语法
1 2
| TYPE TABLE_NAME IS TABLE OF DATA_TYPE [NOT NULL] INDEX BY BINARY_INTEGER;
|
样例
1 2 3 4 5 6 7 8 9 10 11 12 13
| set serveroutput on declare TYPE a IS TABLE OF Student%ROWTYPE; begin select * into a from Student; dbms_output.put_line(a(1).sid); dbms_output.put_line(a(1).sname); dbms_output.put_line(a(1).ssex); dbms_output.put_line(a(1).sage); end; /
|
其它功能
- count 计数
- delete 删除行
- first 第一个索引值
- next 下一个索引值
- last 最后一行记录的索引值
一个坑
做了一个大坑,今天终于填上了。在 Simple PL/SQL 对游标的理解 一讲中我有一个不能实行的问题,还一直以为是游标或者本地读取失败的BUG。结果是
不能直接对表变量赋值,赋值需要使用下标,如下面的的例子。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
| set serveroutput on declare type course_table is table of course%rowtype index by binary_integer; fku course_table; v_num number:=0; cursor cur_cou is select * from course; begin for tmp in cur_cou loop v_num:=v_num+1; select * into fku(v_num) from course where tmp.cid=cid ; end loop; if fku.count=0 then dbms_output.put_line('没有记录'); else dbms_output.put_line('有'||fku.count||'条记录'); end if; end; /
|