sql >> Databáze >  >> RDS >> Oracle

Jak používat parametry v klauzuli „kde hodnota v...“?

Použití dynamického SQL je z hlediska kódování nejjednodušší přístup. Problém s dynamickým SQL je však v tom, že musíte tvrdě analyzovat každou odlišnou verzi dotazu, což má nejen potenciál zatížit váš CPU, ale má potenciál zaplavit váš sdílený fond spoustou nesdílených SQL příkazů, out příkazy, které chcete uložit do mezipaměti, což způsobuje tvrdší analýzy a chyby fragmentace sdíleného fondu. Pokud to spouštíte jednou denně, pravděpodobně to není hlavní problém. Pokud to stovky lidí provádějí tisíckrát denně, je to pravděpodobně hlavní problém.

Příklad dynamického SQL přístupu

SQL> ed
Wrote file afiedt.buf

  1  declare
  2    l_deptnos  varchar2(100) := '10,20';
  3    l_rc       sys_refcursor;
  4    l_dept_rec dept%rowtype;
  5  begin
  6    open l_rc for 'select * from dept where deptno in (' || l_deptnos || ')';
  7    loop
  8      fetch l_rc into l_dept_rec;
  9      exit when l_rc%notfound;
 10      dbms_output.put_line( l_dept_rec.dname );
 11    end loop;
 12    close l_rc;
 13* end;
SQL> /
ACCOUNTING
RESEARCH

PL/SQL procedure successfully completed.

Alternativně můžete použít sbírku. To má tu výhodu, že se generuje jeden sdílený kurzor, takže se nemusíte starat o těžkou analýzu nebo zahlcení sdíleného fondu. Ale pravděpodobně to vyžaduje trochu více kódu. Nejjednodušší způsob, jak se vypořádat s kolekcemi

SQL> ed
Wrote file afiedt.buf

  1  declare
  2    l_deptnos  tbl_deptnos := tbl_deptnos(10,20);
  3  begin
  4    for i in (select *
  5                from dept
  6               where deptno in (select column_value
  7                                  from table(l_deptnos)))
  8    loop
  9      dbms_output.put_line( i.dname );
 10    end loop;
 11* end;
SQL> /
ACCOUNTING
RESEARCH

PL/SQL procedure successfully completed.

Pokud na druhou stranu opravdu musíte začít se seznamem hodnot odděleným čárkami, pak budete muset tento řetězec analyzovat do kolekce, než jej budete moci použít. Existují různé způsoby, jak analyzovat oddělený řetězec – mým osobním favoritem je použití regulárních výrazů v hierarchickém dotazu, ale určitě byste mohli napsat i procedurální přístup

SQL> ed
Wrote file afiedt.buf

  1  declare
  2    l_deptnos     tbl_deptnos;
  3    l_deptno_str  varchar2(100) := '10,20';
  4  begin
  5    select regexp_substr(l_deptno_str, '[^,]+', 1, LEVEL)
  6      bulk collect into l_deptnos
  7      from dual
  8   connect by level <= length(replace (l_deptno_str, ',', NULL));
  9    for i in (select *
 10                from dept
 11               where deptno in (select column_value
 12                                  from table(l_deptnos)))
 13    loop
 14      dbms_output.put_line( i.dname );
 15    end loop;
 16* end;
 17  /
ACCOUNTING
RESEARCH

PL/SQL procedure successfully completed.


  1. Vysvětlení velikosti úložiště „datetime2“ na serveru SQL

  2. Jak upgradovat PostgreSQL z verze 9.6 na verzi 10.1 bez ztráty dat?

  3. Převod výsledků Select do skriptu Insert - SQL Server

  4. 12 Doporučené postupy zabezpečení MySQL/MariaDB pro Linux