sql >> Database teknologi >  >> RDS >> Oracle

Opdater resultaterne af en SELECT-sætning

Jeg har ikke set et formelt navn for dette. Oracle SQL Reference henviser blot til opdatering af en underforespørgsel. Jeg har en tendens til at tænke på det som en form for "visningsopdatering", hvor underforespørgslen er i in-line-visning.

Ja, det virker, når et antal tabeller samles, men underlagt reglerne for opdatering af visning. Det betyder, at kun én af visningens basistabeller kan opdateres, og denne tabel skal "nøglebevares" i visningen:dvs. dens rækker skal kun kunne vises én gang i visningen. Dette kræver, at alle andre tabeller i visningen (underforespørgsel) refereres via fremmednøglebegrænsninger på tabellen, der skal opdateres.

Nogle eksempler kan hjælpe. Ved at bruge standard Oracle EMP- og DEPT-tabeller, hvor EMP.EMPNO er ​​defineret som den primære nøgle for EMP, og EMP.DEPTNO er ​​defineret som en fremmednøgle til DEPT.DEPTNO, er denne opdatering tilladt:

update (select emp.empno, emp.ename, emp.sal, dept.dname
        from   emp join dept on dept.deptno = emp.deptno
       )
set sal = sal+100;
 

Men dette er ikke:

-- DEPT is not "key-preserved" - same DEPT row may appear -- several times in view update (select emp.ename, emp.sal, dept.deptno, dept.dname from emp join dept on dept.deptno = emp.deptno ) set dname = upper(dname);

Med hensyn til ydeevne:optimeringsværktøjet vil (skal) identificere den basistabel, der skal opdateres under parsing, og joinforbindelser til en anden tabel vil blive ignoreret, da de ikke har nogen indflydelse på den opdatering, der skal udføres - som dette AUTOTRACE-output viser:

SQL> update (select emp.ename, emp.sal, dept.dname
  2              from   emp join dept on dept.deptno = emp.deptno
  3             )
  4      set sal = sal-1;

33 rows updated.


Execution Plan
----------------------------------------------------------
Plan hash value: 1507993178

------------------------------------------------------------------------------------
| Id  | Operation           | Name         | Rows  | Bytes | Cost (%CPU)| Time     |
------------------------------------------------------------------------------------
|   0 | UPDATE STATEMENT    |              |    33 |   495 |     3   (0)| 00:00:01 |
|   1 |  UPDATE             | EMP          |       |       |            |          |
|   2 |   NESTED LOOPS      |              |    33 |   495 |     3   (0)| 00:00:01 |
|   3 |    TABLE ACCESS FULL| EMP          |    33 |   396 |     3   (0)| 00:00:01 |
|*  4 |    INDEX UNIQUE SCAN| SYS_C0010666 |     1 |     3 |     0   (0)| 00:00:01 |
------------------------------------------------------------------------------------

Predicate Information (identified by operation id):
---------------------------------------------------

   4 - access("EMP"."DEPTNO"="DEPT"."DEPTNO")
 

(Bemærk, at der aldrig er adgang til tabel DEPT, selvom DEPT.DNAME vises i underforespørgslen).



  1. hvordan tilføjer man superprivilegier til mysql-databasen?

  2. ODP.NET Oracle.ManagedDataAcess tilfældige ORA-12570-fejl

  3. PL/SQL-forespørgsel IN kommaafgrænset streng

  4. CodeIgniter-forespørgsel:Hvordan flytter man en kolonneværdi til en anden kolonne i samme række og gemmer den aktuelle tid i den oprindelige kolonne?