如何使用 pl/sql 为多行填充相同的值

Posted

技术标签:

【中文标题】如何使用 pl/sql 为多行填充相同的值【英文标题】:How to populate same value for multiple rows using pl/sql 【发布时间】:2017-08-11 17:36:40 【问题描述】:

如果员工id 相同,我如何将相同的数据填充到多行中。无需每次都查询表 例如。 如果我从员工表中得到以下行

EMPLID  CHANGETIME
------  --------------
1234    8/10/2017
1234    8/11/2017

对于上述员工,我需要查询 NAME 表以获取姓名并填充两行。

EMPLID  CHANGETIME  FirstNAME LastNAME
------  ----------  --------- --------
1234    08/10/17    JOHN       MATHEW
1234    08/11/17    JOHN       MATHEW

当我第一次查询时,我想将它存储在数组或某个变量中,如果 EMPLID 与前一个匹配,则填充相同的变量。

只是想这样做以提高性能。任何提示都会有所帮助。

现在我正在使用批量插入类型表,每次从 EMPLOYEE 表中获取一行时它都会搜索 NAME 表

【问题讨论】:

【参考方案1】:

我会使用连接来获取员工姓名(也在 pl/sql 中),例如: SELECT e.emplid, e.first_name, e.last_name, c.changetime FROM employee_changes c INNER JOIN employee e ON e.emplid = c.emplid WHERE c.change_time > sysdate - 30 ORDER BY e.emplid, c.change_time

如果你想选择可以用作光标...

【讨论】:

【参考方案2】:

我认为您需要一些额外的标准,例如“最后更改时间”。 在这种情况下,您可以编写如下代码:

SELECT e.EMPLID, e.CHANGETIME, n.FirstNAME, n.LastNAME
  FROM Employee e, NAME n
 WHERE e.emplid = n.emplid
   AND e.changetime = (SELECT MAX(e1.changetime)
                         FROM Employee e1
                        WHERE e1.emplid = e.emplid);

“对于每个员工,只需获取 de max changetime”

【讨论】:

【参考方案3】:

如果您使用的是 11g,则应考虑使用结果缓存功能。这允许我们定义返回值存储在内存中的函数。像这样的:

create or replace function get_name 
    (p_empid pls_integer)
    return varchar2
    result_cache relies_on (names)
is
  return_value varchar2(30);
begin
    select empname into return_value  
    from names
    where empid = p_empid;
    return return_value;
end get_name;
/   

注意 RELIES_ON 子句:这是一个选项,但它表明缓存仅对缓慢变化的表有用。如果 NAMES 表中有大量流失,Oracle 将继续刷新缓存,您将不会获得太多好处。但至少结果是正确的——这是你目前的方法无法保证的。

这是一个示例。忽略经过的时间,但要注意在第二次通话中获得相同的员工姓名所需的努力:

SQL> set autotrace on 
SQL> set timing on
SQL> select get_name(7934) from dual
  2  /

GET_NAME(7934)
------------------------------------------------------------------------------------------------------------------------------------------------------
MILLER

Elapsed: 00:00:01.25

Execution Plan
----------------------------------------------------------
Plan hash value: 1388734953

-----------------------------------------------------------------
| Id  | Operation        | Name | Rows  | Cost (%CPU)| Time     |
-----------------------------------------------------------------
|   0 | SELECT STATEMENT |      |     1 |     2   (0)| 00:00:01 |
|   1 |  FAST DUAL       |      |     1 |     2   (0)| 00:00:01 |
-----------------------------------------------------------------

Statistics
----------------------------------------------------------
        842  recursive calls
        166  db block gets
       1074  consistent gets
         44  physical reads
      30616  redo size
        499  bytes sent via SQL*Net to client
        437  bytes received via SQL*Net from client
          2  SQL*Net roundtrips to/from client
        134  sorts (memory)
          0  sorts (disk)
          1  rows processed

SQL>

第二次通话:

SQL> r
  1* select get_name(7934) from dual

GET_NAME(7934)
------------------------------------------------------------------------------------------------------------------------------------------------------
MILLER

Elapsed: 00:00:00.13

Execution Plan
----------------------------------------------------------
Plan hash value: 1388734953

-----------------------------------------------------------------
| Id  | Operation        | Name | Rows  | Cost (%CPU)| Time     |
-----------------------------------------------------------------
|   0 | SELECT STATEMENT |      |     1 |     2   (0)| 00:00:01 |
|   1 |  FAST DUAL       |      |     1 |     2   (0)| 00:00:01 |
-----------------------------------------------------------------    

Statistics
----------------------------------------------------------
          0  recursive calls
          0  db block gets
          0  consistent gets
          0  physical reads
          0  redo size
        499  bytes sent via SQL*Net to client
        437  bytes received via SQL*Net from client
          2  SQL*Net roundtrips to/from client
          0  sorts (memory)
          0  sorts (disk)
          1  rows processed

SQL> 

文档中有很多关于这个漂亮功能的内容。 Find out more.

【讨论】:

以上是关于如何使用 pl/sql 为多行填充相同的值的主要内容,如果未能解决你的问题,请参考以下文章

如何在 PL/SQL 中使用循环多次运行相同的查询?

如何在 pl/sql 函数中的变量中存储多行?

将行拆分为多行 PL/SQL

如何使用 PL/SQL 正则表达式将 HTML 标记及其内容替换为相同数量的“?s”?

如何编写 PL 以返回通过服务总线中的 DB 适配器自动生成强类型 XSD 的多行? (甲骨文 PL/SQL)

从 oracle PL/SQL 查看变量的值