CREATE OR REPLACE PROCEDURE TEST_RECORD
AS
TYPE user_record_type IS RECORD(
id usersid%TYPE
login_id userslogin_id%TYPE
name usersname%TYPE);
u_r_t user_record_type;
BEGIN
FOR recd IN (SELECT * FROM users) LOOP
SELECT idlogin_idname INTO u_r_t FROM users WHERE id=recdid;
dbms_outputput_line(ID: ||u_r_tid || LOGIN_ID: ||u_r_tlogin_id|| NAME: ||u_r_tname);
END LOOP;
NULL;
END;
一什么是记录(Record)?
由单行多列的标量构成的复合结构可以看做是一种用户自定义数据类型组成类似于多维数组
将一个或多个标量封装成一个对象进行操作是一种临时复合对象类型
记录可以直接赋值RECORD :=RECORD
记录不可以整体比较
记录不可以整体判断为空
二%ROWTYPE和记录(Record)?
请区别%ROWTYPE和记录(Record)类型%ROWTYPE可以说是Record的升级简化版
区别在与前者结构为表结构后者为自定义结构二者在使用上没有很大区别前者方便后者灵活在实际中根据情况来具体决定使用
Record + PL/SQL表可以进行数据的多行多列存储
三如何创建和使用记录?
①创建记录类型
语法
TYPE 记录名 IS RECORD
(
filed type [NOT NULL] [=eXPr]
filedN typen [NOT NULL] [=exprn]
)
其中filed是标量的名字
②声明记录类型变量
记录类型变量名 记录类型
③填充记录
④访问记录成员
记录类型变量名filed
记录类型变量名filedN
注意
表字段类型修改后还需要修改记录字段类型有时候可能会忘记从而出现错误
对于记录内每个字段(filed)可以指定也可以使用%TYPE和%ROWTYPE动态指定记录字段类型
好处是表字段发生变化记录字段自动改变但是由于每次执行前遇到%TYPR或%ROWTYPE
数据库系统都会去查看对应表字段类型会造成一定的数据库开销如果系统中大量使用记录类型则对性能会有一定影响
另外如果删除了某一字段而自定义记录中使用了该字段也会有可能忘记删除该字段
对数据库负荷偏低的系统性能问题一般可以不重点关注但是对于高负荷数据库服务器
各个环节都要考虑性能问题每处节省一点出来性能整体就有很大提高
语法
TYPE 记录名 IS RECORD
(
filed tableFiled%Type [NOT NULL] [=eXPr]
filed tableFiled%Type [NOT NULL] [=eXPr]
filedn tableFiled%Type [NOT NULL] [=exprn]
);
例子记录可以整体赋值
Declare
Type EmpType is Record(
EMPNO number()
ENAME varchar()
JOB varchar()
SAL number()
DEPTNO number()
);
EmpRec EmpType;
EmpRec EmpType;
Begin
EmpRecEmpno:=;
EmpRecEname:=SMITH;
EmpRecJob:=CLERK;
EmpRecSal:=;
EmpRecDeptno:=;
EmpRec := EmpRec;
DBMS_outputput_line(EmpRecempno);
End;
例子记录不可以整体比较只可以比较记录字段
Declare
Type EmpType is Record(
EMPNO number()
ENAME varchar()
JOB varchar()
SAL number()
DEPTNO number()
);
EmpRec EmpType;
EmpRec EmpType;
Begin
EmpRecEmpno:=;
EmpRecEname:=SMITH;
EmpRecJob:=CLERK;
EmpRecSal:=;
EmpRecDeptno:=;
if EmpRecsal < EmpRecsal then
DBMS_outputput_line(Xiao Xiao Xiao);
end if;
End;
例子记录不可以整体判断为空只可以判断记录字段
Declare
Type EmpType is Record(
EMPNO number()
ENAME varchar()
JOB varchar()
SAL number()
DEPTNO number()
);
EmpRec EmpType;
Begin
if EmpRecename is null then
DBMS_outputput_line(Kong Kong Kong);
end if;
End;
例子使用%TYPE和%ROWTYPE动态指定记录字段
DECLARE
Type MyRecType Is Record
(
RENO EMPAEMPNO%Type
RENAME EMPAENAME%Type
RJOB EMPAJOB%Type
);
EmpRec MyRecType;
Begin
Select EMPNO ENAME JOB InTo EmpRec From empa Where empaEMPNO = ;
If EmpRecRJOB = CLERK Then
DBMS_OUTPUTPUT_LINE(Name: ||EmpRecRENAME);
End If;
End;
例子数据集中的记录和记录类型中的数据关系
DECLARE
Type MyRecType Is Record
(
RENO EMPAEMPNO%Type
RENAME EMPAENAME%Type
RJOB EMPAJOB%Type
);
EmpRec MyRecType;
vJob EMPAJOB%Type;
Begin
Select EMPNO ENAME JOB InTo EmpRec From empa Where empaEMPNO = ;
DBMS_OUTPUTPUT_LINE(MyRecTypeRJOB: ||EmpRecRJOB);
EmpRecRJOB := 修改值后 ;
DBMS_OUTPUTPUT_LINE(MyRecTypeRJOB: ||EmpRecRJOB);
Select JOB InTo vJob from empa Where empaEMPNO = EmpRecRENO;
DBMS_OUTPUTPUT_LINE(EMPAJOB: ||vJob);
End;
/
四使用记录向表中插入数据?
根据表结构合理安排记录字段比如主外键
如果用记录(RECORD)插入数据那么只能使用记录成员
如果用%ROWTYPE插入数据可以直接使用%ROWTYPE
例子使用记录成员向表中插入数据
DECLARE
Type MyRecType Is Record
(
RENO EMPAEMPNO%Type
RENAME VARCHAR()
RJOB EMPAJOB%Type
);
EmpRec MyRecType;
Begin
Select EMPNO ENAME JOB InTo EmpRec From empa Where empaEMPNO = ;
DBMS_OUTPUTPUT_LINE(EmpRecRENO|| ||EmpRecRENAME|| ||EmpRecRJOB);
EmpRecRENO := ;
EmpRecRENAME := 杰克;
EmpRecRJOB := 办事员;
Insert InTo empa(EMPNOENAMEJOB) Values(EmpRecRENO EmpRecRENAMEEmpRecRJOB);
Select EMPNO ENAME JOB InTo EmpRec From empa Where empaEMPNO = ;
DBMS_OUTPUTPUT_LINE(EmpRecRENO|| ||EmpRecRENAME|| ||EmpRecRJOB);
End;
五使用记录更新数据?
如果用记录(RECORD)更新数据那么只能使用记录成员
如果用%ROWTYPE更新数据可以直接使用%ROWTYPE
例子使用%ROWTYPE向表中插入数据
DECLARE
vEmp empa%RowType;
Begin
Select * InTo vEmp From empa Where empaEMPNO = ;
UpDate empa Set ROW = vEmp Where EMPNO = ;
End;
六使用记录删除数据?
删除记录时只能在delete语句的where子句中使用记录成员