Oracle
 sql >> Datenbank >  >> RDS >> Oracle

Schnellerer Weg zum Einfügen per Skript in Oracle?

Problem

Die Analysezeit kann bei bestimmten Arten von Anweisungen exponentiell ansteigen, insbesondere bei INSERT ALL . Zum Beispiel:

--Clear any cached statements, so we can consistently reproduce the problem.
alter system flush shared_pool;
alter session set sql_trace = true;

--100 rows
INSERT ALL
    INTO FileIds(Id,FileTypeGroupId) VALUES(1, 1)
    ...
    repeat 100 times
    ...
select * from dual;

--500 rows
INSERT ALL
    INTO FileIds(Id,FileTypeGroupId) VALUES(1, 1)
    ...
    repeat 500 times
    ...
select * from dual;

alter session set sql_trace = false;

Führen Sie die Ablaufverfolgungsdatei durch tkprof, und Sie können sehen, dass die Analysezeit für eine große Anzahl von Zeilen dramatisch ansteigt. Zum Beispiel:

100 Zeilen:

call     count       cpu    elapsed       disk      query    current        rows
------- ------  -------- ---------- ---------- ---------- ----------  ----------
Parse        1      0.06       0.05          0          1          0           0
Execute      1      0.00       0.00          0        100        303         100
Fetch        0      0.00       0.00          0          0          0           0
------- ------  -------- ---------- ---------- ---------- ----------  ----------
total        2      0.06       0.05          0        101        303         100

500 Zeilen:

call     count       cpu    elapsed       disk      query    current        rows
------- ------  -------- ---------- ---------- ---------- ----------  ----------
Parse        1     14.72      14.55          0          0          0           0
Execute      1      0.01       0.02          0        502       1518         500
Fetch        0      0.00       0.00          0          0          0           0
------- ------  -------- ---------- ---------- ---------- ----------  ----------
total        2     14.74      14.58          0        502       1518         500

Lösungen

  1. Teilen Sie Ihre große Aussage in mehrere kleinere Aussagen auf. Es ist schwierig, die optimale Größe zu finden. Bei einigen Versionen von Oracle gibt es eine magische Anzahl von Zeilen, die das Problem verursachen. Normalerweise gehe ich für etwa 100 Zeilen - genug, um die meisten Vorteile der Gruppierung von Anweisungen zu nutzen, aber niedrig genug, um den Parsing-Bug zu vermeiden. ODER...
  2. Probieren Sie insert into ... select ... from dual union all ... Methode statt. Es läuft normalerweise viel schneller, obwohl seine Parsing-Leistung auch mit der Größe erheblich abnehmen kann.
  3. Aktualisieren Sie Oracle. Die Analyseleistung wurde in neueren Versionen verbessert. Ich kann dieses Problem in Version 12.2 nicht mehr reproduzieren.

Warnung

Lernen Sie daraus nicht die falsche Lehre. Wenn Sie sich Sorgen um die SQL-Leistung machen, ist es in 99 % der Fälle besser, wenn Sie ähnliche Dinge zusammenfassen, anstatt sie zu trennen. Du machst die Dinge richtig, du bist gerade auf einen seltsamen Fehler gestoßen. (Ich habe My Oracle Support durchsucht, konnte aber keinen offiziellen Fehler dafür finden.)