8

使用 PL/SQL 是否会出现一种情况,比如在异常情况下,隐式游标将无法关闭?

我知道隐式游标应该在使用后自行关闭,但只是想知道是否存在这种情况可能并非如此的情况,如果可能的话,什么样的补救措施是个好主意。

4

3 回答 3

2

COMMIT or ROLLBACK失败时游标不会自动关闭
建议使用游标时使用以下路由:

-- before using the cursor
    IF your_cursor %ISOPEN THEN
         CLOSE your_cursor;
    END IF;
   OPEN your_cursor;

-- after using the cursor
         CLOSE your_cursor;
-- when exception
    IF your_cursor %ISOPEN THEN
         CLOSE your_cursor;
    END IF;
于 2013-02-22T19:03:58.460 回答
1

我将假设您正在谈论隐式游标,即 SELECT INTO... 或在 PL/SQL 块中执行的 DML 语句,而不是 FOR 循环。

与显式游标一样,隐式游标具有属性;你可以使用SQL%NOTFOUND(而不是CURSOR_NAME%NOTFOUND例如。

引用关于隐式游标属性的11.1 文档SQL%ISOPEN

始终返回 FALSE,因为数据库在执行关联的 SQL 语句后会自动关闭 SQL 游标。

我相信,这应该被认为意味着游标将在执行后关闭,无论是否引发异常。毕竟,由于异常而停止的执行仍然是执行的 SQL 语句。

原因已从11.2 文档中删除。

SQL%ISOPEN 始终具有值 FALSE。

它似乎已被添加到关于隐式游标的章节中

SQL%ISOPEN 总是返回 FALSE,因为隐式游标总是在其关联语句运行后关闭。

由于最后一个问题的答案,光标是否关闭并不重要,“什么​​样的补救措施是个好主意。” . 引用同一章:

您无法控制隐式游标,但可以从其属性中获取信息。

所以不行。无法补救;不可能显式关闭隐式打开的游标。

您可能想要测试的一件事是您是否可以提高ORA-0100: Maximum open cursors exceeded using only implicit cursors,因为这是我能想到的最糟糕的后果。

于 2013-02-23T22:09:42.833 回答
1

让我们将“隐式游标”定义为在 FOR 循环中执行的 SELECT 语句。

从实际的角度来看 - 无论隐式光标是否可能保持打开状态,重要的问题是“你能做些什么?”。据我所知,这个问题的答案是“没有”。您没有可使用的游标变量,没有办法(据我所知)访问隐式游标,因此您真的无法影响它。

你可以做两件事。首先是完全避免使用隐式游标。仅使用显式游标,完成打开、获取、关闭等所有步骤。这为您提供了最大程度的控制。如果你喜欢这种事情,那就去吧。

另一方面,您可以使用隐式游标而不必担心。我很好,不用担心。:-) 不过说真的,隐式游标比显式游标在 IMO 上要好得多。需要编写的代码更少,因此要搞砸的代码也更少。在某些情况下,系统可以优化隐式游标的使用,而无需您编写一堆额外的代码。您编写的代码更清晰,更容易理解 - 如果您在一个单独的商店工作,则无需担心编写和维护所有代码,但在 Corporateville 中,我们经常必须编写其他人将维护的代码,反之亦然,并且尽可能交出最干净、最清晰的代码被认为是礼貌的。有时(例如将游标变量从 Oracle 外部交给调用者时)需要显式游标,但对于大多数代码,我使用隐式 FOR-LOOP 游标 -并且喜欢!(对于那些能回忆起来自哪里的人来说,还有额外的奖励积分:-)

分享和享受。

于 2013-03-04T12:42:13.123 回答