Oracle 23c 中 RETURNING INTO 子句

2023-10-23 16:20:25 浏览数 (2)

在执行INSERT、UPDATE 和 DELETE 语句时,现在我们可以通过RETURNING INTO 子句返回受影响数据的新值或者旧值。

在 Oracle 23c中,INSERT、UPDATE 和 DELETE 语句的 RETURNING INTO 子句得到了增强,可以返回受相应语句影响的旧值和新值。这允许开发人员对每个 DML 类型使用相同的逻辑来获取语句执行前和执行后的值。旧值和新值仅对 UPDATE 语句有效。INSERT 语句不返回旧值,DELETE 语句不返回新值。

作为 SQL 命令执行的一部分,能够获取受 INSERT、UPDATE 和 DELETE 语句影响的旧值和新值,为开发人员提供了读取这些值的统一方法,并减少了数据库必须执行的工作量。

完整的 UPDATE 语法:

其中,RETURNING 子句语法:

你可以为具有单个基表的表、视图和物化视图指定此子句。

当对单行进行操作时,带有returning_clause 的DML 语句可以使用受影响的行、rowid 和受影响行的REF 来检索列值,并将它们存储在主变量或PL/SQL 变量中。

当对多行进行操作时,带有returning_clause 的DML 语句从涉及绑定数组中受影响的行的表达式、rowid 和REF 返回值。

expr

expr 列表中的每一项都必须是有效的表达式语法。

INTO

INTO 子句指示更改的行的值将存储在 data_item 列表中指定的变量中。

data_item

每个 data_item 都是一个主变量或 PL/SQL 变量,用于存储检索到的 expr 值。

对于 RETURNING 列表中的每个表达式,必须在 INTO 列表中指定相应的类型兼容的 PL/SQL 变量或主变量。

给定表中的列 c1 和 c2,您可以为列 c1 指定 OLD(例如 OLD c1)。您还可以为列表达式引用的列指定 OLD(例如 c1 OLD c2)。当列指定OLD时,返回更新前的列值。对于列表达式引用的列,返回的是使用更新前的列值计算列表达式的结果。

可以为列或表达式中引用的列显式指定 NEW 以返回更新后的列值,或使用列更新后值的表达式结果。

当列或表达式中同时省略 OLD 和 NEW 时,将返回更新后列值或使用更新后列值计算的表达式结果。

限制

以下限制适用于 RETURNING 子句:

  • expr 的限制如下:
    • ‍对于 UPDATE 和 DELETE 语句,每个 expr 必须是简单表达式或单集聚合函数表达式。您不能在同一个 returned_clause 中组合简单表达式和单集聚合函数表达式。对于 INSERT 语句,每个 expr 必须是一个简单表达式。INSERT 语句 RETURNING 子句中不支持聚合函数。
    • 单集聚合函数表达式不能包含 DISTINCT 关键字。
  • 如果 expr 列表包含主键列或其他 NOT NULL 列,并且表上定义了 BEFORE UPDATE 触发器,则更新语句将失败。
  • 您不能为多表插入指定returning_clause。
  • 不能将此子句与并行 DML 或远程对象一起使用。
  • 您无法使用此子句检索 LONG 类型。
  • 您不能为已定义 INSTEAD OF 触发器的视图指定此子句。

在 UPDATE 中使用 RETURNING 子句示例:

以下示例从更新的行返回值并将结果存储在 PL/SQL 变量 bnd1、bnd2、bnd3 中:

代码语言:javascript复制
UPDATE employees
  SET job_id ='SA_MAN', salary = salary   1000, department_id = 140
  WHERE last_name = 'Jones'
  RETURNING salary*0.25, last_name, department_id
    INTO :bnd1, :bnd2, :bnd3;

以下示例显示您可以在返回子句的表达式中指定单集聚合函数:

代码语言:javascript复制
UPDATE employees
   SET salary = salary * 1.1
   WHERE department_id = 100
   RETURNING SUM(salary) INTO :bnd1;

0 人点赞