Probleem
De parseertijd kan exponentieel toenemen met bepaalde soorten instructies, vooral INSERT ALL
. Bijvoorbeeld:
--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;
Voer het traceringsbestand uit via tkprof en u kunt zien dat de Parse-tijd dramatisch toeneemt voor een groot aantal rijen. Bijvoorbeeld:
100 rijen:
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 rijen:
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
Oplossingen
- Breek je grote statement op in meerdere kleinere statements. Het is moeilijk om de optimale maat te vinden. Op sommige versies van Oracle is er een magisch aantal rijen dat het probleem zal veroorzaken. Ik ga meestal voor ongeveer 100 rijen - genoeg om de meeste voordelen van het groeperen van statements te krijgen, maar laag genoeg om de parseerbug te vermijden. OF...
- Probeer de
insert into ... select ... from dual union all ...
methode in plaats daarvan. Het werkt meestal veel sneller, hoewel de parseerprestaties ook aanzienlijk kunnen verslechteren met de grootte. - Oracle upgraden. De parseerprestaties zijn verbeterd in nieuwere versies. Ik kan dit probleem niet meer reproduceren in versie 12.2.
Waarschuwing
Trek hier niet de verkeerde les uit. Als je je zorgen maakt over de SQL-prestaties, kun je 99% van de tijd beter gelijkaardige dingen bij elkaar groeperen in plaats van ze uit elkaar te halen. Je doet de dingen op de juiste manier, je liep alleen tegen een rare bug aan. (Ik heb in My Oracle Support gezocht maar kon hier geen officiële bug voor vinden.)