我在PL / SQL中的光标术语上有点生疏。有人知道吗?
答案 0 :(得分:40)
隐式游标是Oracle在您执行查询时“自动”为您创建的游标。编码更简单,但遭受
的困扰实施例
SELECT col INTO var FROM table WHERE something;
显式光标是您自己创建的光标。它需要更多代码,但可以提供更多控制 - 例如,如果您只想要第一条记录而不关心是否有其他记录,则可以只是打开 - 获取 - 关闭。
实施例
DECLARE
CURSOR cur IS SELECT col FROM table WHERE something;
BEGIN
OPEN cur;
FETCH cur INTO var;
CLOSE cur;
END;
答案 1 :(得分:17)
显式游标在声明块中定义如下:
DECLARE
CURSOR cur IS
SELECT columns FROM table WHERE condition;
BEGIN
...
隐式游标直接在代码块中实现:
...
BEGIN
SELECT columns INTO variables FROM table where condition;
END;
...
答案 2 :(得分:4)
1.CURSOR:当PLSQL发出sql语句时,它会创建私有工作区 解析&执行sql语句称为游标。
2.IMPLICIT:当任何PL / SQL可执行块发出sql语句时。 PL / SQL创建隐式游标并自动管理 implcit open& amp;关闭发生。它在sql语句返回时使用 只有一行。它有4个属性SQL%ROWCOUNT,SQL%FOUND, SQL%NOTFOUND,SQL%ISOPEN。
3.EXPLICIT:创建&由程序员管理。它需要每一个 时间明确开放,取得&关。它在sql语句时使用 返回多行。它还有4个属性 CUR_NAME%ROWCOUNT,CUR_NAME%FOUND,CUR_NAME%NOTFOUND, CUR_NAME%ISOPEN。它使用循环处理多行。 程序员也可以将参数传递给显式游标。
declare
cursor emp_cursor
is
select id,name,salary,dept_id
from employees;
v_id employees.id%type;
v_name employees.name%type;
v_salary employees.salary%type;
v_dept_id employees.dept_id%type;
begin
open emp_cursor;
loop
fetch emp_cursor into v_id,v_name,v_salary,v_dept_id;
exit when emp_cursor%notfound;
dbms_output.put_line(v_id||', '||v_name||', '||v_salary||','||v_dept_id);
end loop;
close emp_cursor;
end;
答案 3 :(得分:3)
显式游标是您声明的游标,如:
CURSOR my_cursor IS
SELECT table_name FROM USER_TABLES
隐式游标是为支持您编写的任何内嵌SQL(静态或动态)而创建的。
答案 4 :(得分:3)
这些天隐式游标比显式游标更有效。
http://www.oracle.com/technology/oramag/oracle/04-sep/o54plsql.html
http://asktom.oracle.com/pls/asktom/f?p=100:11:0::::P11_QUESTION_ID:1205168148688
答案 5 :(得分:3)
回答第一个问题。直接来自Oracle documentation
游标是指向私有SQL的指针 存储信息的区域 处理特定的SELECT或DML 言。
答案 6 :(得分:3)
隐式游标需要匿名缓冲区内存。
显式游标可以通过使用它们的名称一次又一次地执行。它们存储在用户定义的内存空间中,而不是存储在匿名缓冲区内存中,因此可以在以后轻松访问。
答案 7 :(得分:2)
使用显式游标,您可以完全控制如何访问数据库中的信息。您决定何时打开游标,何时从游标(因此从游标的SELECT语句中的一个或多个表)获取FETCH记录要获取的记录数以及何时关闭游标。通过检查光标属性,可以获得有关光标当前状态的信息。
有关详细信息,请参阅http://www.unix.com.ua/orelly/oracle/prog2/ch06_03.htm。
答案 8 :(得分:1)
Google是您的朋友:http://docstore.mik.ua/orelly/oracle/prog2/ch06_03.htm
PL / SQL发出隐式游标 每当执行SQL语句时 直接在你的代码中,只要那样 代码不使用显式 光标。它被称为“隐含的” 游标,因为你,开发人员,做 没有显式声明游标 SQL语句。
显式游标是SELECT 明确定义的语句 在你的宣言部分 代码,并在此过程中分配了一个 名称。没有这样的东西 用于UPDATE,DELETE的显式游标, 和INSERT语句。
答案 9 :(得分:1)
游标是Oracle表上的SELECTed窗口,这意味着Oracle表中存在一组记录,并满足某些条件。游标也可以选择表的所有内容。使用游标,您可以操作Oracle列,在结果中对它们进行别名处理。隐式游标的示例如下:
BEGIN
DECLARE
CURSOR C1
IS
SELECT DROPPED_CALLS FROM ALARM_UMTS;
C1_REC C1%ROWTYPE;
BEGIN
FOR C1_REC IN C1
LOOP
DBMS_OUTPUT.PUT_LINE ('DROPPED CALLS: ' || C1_REC.DROPPED_CALLS);
END LOOP;
END;
END;
/
使用FOR ... LOOP ... END LOOP当光标记录全部被分析时,你自动打开和关闭光标。
显式游标的示例如下:
BEGIN
DECLARE
CURSOR C1
IS
SELECT DROPPED_CALLS FROM ALARM_UMTS;
C1_REC C1%ROWTYPE;
BEGIN
OPEN c1;
LOOP
FETCH c1 INTO c1_rec;
EXIT WHEN c1%NOTFOUND;
DBMS_OUTPUT.PUT_LINE ('DROPPED CALLS: ' || C1_REC.DROPPED_CALLS);
END LOOP;
CLOSE c1;
END;
END;
/
在显式游标中,您以明确的方式打开和关闭游标,检查记录的存在并说明退出条件。
答案 10 :(得分:1)
隐式游标只返回一条记录并自动调用。但是,显式游标是手动调用的,可以返回多个记录。
答案 11 :(得分:1)
我知道这是一个老问题,但是,我认为最好添加一个实际的例子,从性能的角度来看两者之间的区别。
从性能的角度来看,隐式游标更快。
让我们看看两者之间的表现差异:
SQL> SET SERVEROUTPUT ON
SQL> DECLARE
2 l_loops NUMBER := 100000;
3 l_dummy dual.dummy%TYPE;
4 l_start NUMBER;
5
6 CURSOR c_dual IS
7 SELECT dummy
8 FROM dual;
9 BEGIN
10 l_start := DBMS_UTILITY.get_time;
11
12 FOR i IN 1 .. l_loops LOOP
13 OPEN c_dual;
14 FETCH c_dual
15 INTO l_dummy;
16 CLOSE c_dual;
17 END LOOP;
18
19 DBMS_OUTPUT.put_line('Explicit: ' ||
20 (DBMS_UTILITY.get_time - l_start) || ' hsecs');
21
22 l_start := DBMS_UTILITY.get_time;
23
24 FOR i IN 1 .. l_loops LOOP
25 SELECT dummy
26 INTO l_dummy
27 FROM dual;
28 END LOOP;
29
30 DBMS_OUTPUT.put_line('Implicit: ' ||
31 (DBMS_UTILITY.get_time - l_start) || ' hsecs');
32 END;
33 /
Explicit: 332 hsecs
Implicit: 176 hsecs
PL/SQL procedure successfully completed.
因此,显而易见的显着差异。
更多示例here。
答案 12 :(得分:1)
在PL / SQL中,游标是指向此上下文区域的指针。它包含处理语句所需的所有信息。
隐式游标: 当执行SQL语句时,当没有隐式游标时,Oracle会自动创建隐式游标。程序员无法控制隐式游标及其中的信息。
显式光标: 显式游标是程序员定义的游标,用于获得对上下文区域的更多控制。应该在PL / SQL块的声明部分中定义一个显式游标。它是在SELECT语句上创建的,该语句返回多个行。
创建显式游标的语法为:
CURSOR cursor_name IS select_statement;
答案 13 :(得分:0)
Oracle数据库执行的每个SQL语句都有一个与之关联的游标,这是一个用于存储处理信息的私有工作区。 Oracle服务器为所有DML和SELECT语句隐式创建了隐式游标。
您可以声明并使用Explicit游标来命名私有工作区,并在程序块中访问其存储的信息。
答案 14 :(得分:0)
如其他答案中所述,隐式游标更易于使用且不易出错。
并且Implicit vs. Explicit Cursors in Oracle PL/SQL表明隐式游标的速度比显式游标快两倍。
奇怪的是,还没有人提到Implicit FOR LOOP Cursor:
begin
for cur in (
select t.id from parent_trx pt inner join trx t on pt.nested_id = t.id
where t.started_at > sysdate - 31 and t.finished_at is null and t.extended_code is null
)
loop
update trx set finished_at=sysdate, extended_code = -1 where id = cur.id;
update parent_trx set result_code = -1 where nested_id = cur.id;
end loop cur;
end;
关于SO的另一个例子:PL/SQL FOR LOOP IMPLICIT CURSOR。
它比显式形式更短。
这也为updating multiple tables from CTE提供了一个很好的解决方法。
答案 15 :(得分:-2)
...显式
cursor foo是select * from blah; 开始 当关闭光标yada yada yada时打开fetch exit
不要使用它们,使用隐式
cursor foo是select * from blah;
用于foo循环中的n x = n.some_column 结束循环
我认为你甚至可以这样做
for n in(select * from blah)loop ...
坚持隐含,他们关闭自己,他们更可读,他们让生活变得轻松。