sql >> Databasteknik >  >> RDS >> Oracle

Oracle Sequence värden är inte beställda

För det andra, kan jag uppnå beställningen om jag ändrar sekvensen till att vara NOCACHE oavsett ORDER/NOORDER.

ja eftersom NOCACHE faktiskt är ordning eftersom du tvingar en skrivning till sys.seq$-tabellen för varje inkrement, som också måste serialiseras över noder.

--

Jag skulle bestrida det accepterade svaret i den möjliga dubbletten. det är en enorm skillnad i CACHE + ORDER och NOCACHE i RAC. Du förnekar inte CACHEN med ORDER; bara minska dess effektivitet. Jag har personligen sett prestandan för en mellannivåapplikation försämras drastiskt eftersom de använde NOCACHE på en sekvens och åtkomst på flera noder samtidigt. Vi bytte deras sekvens till ORDER CACHE (eftersom de ville ha en cross-rac-order). och prestandan förbättrades drastiskt.

Sammanfattningsvis:Sekvenshastigheten kommer att vara från snabbast till långsammast som "CACHE NOORDER"->"CACHE ORDER" och långt efter "NOCACHE".

Detta är lätt testbart också:

Så vi börjar med en standardsekvens:

SQL> create sequence daz_test start with 1 increment by 1 cache 100 noorder;

Sequence created.

dvs CACHE utan beställning. Nu eldar vi igång två pass. Jag använder en RAC-databas med 4 noder 10.2.0.4 i det här testet:

mitt testskript är helt enkelt

select instance_number from v$instance;              
set serverout on
declare                                                     
 v_timer   timestamp with time zone := systimestamp;  
 v_num number(22);                                    
begin                                                  
 for idx in 1..100000                                 
 loop                                                 
   select daz_test.nextval into v_num from dual;      
 end loop;                                            
 dbms_output.put_line(systimestamp - v_timer);        
end;                                                   
/ 
/

nu kör vi det första testet (CACHE NOORDER):

SESSION 1                                       SESSION 2
SQL> @run_test                                  SQL> @run_test

INSTANCE_NUMBER                                 INSTANCE_NUMBER
---------------                                 ---------------
              2                                               1


PL/SQL procedure successfully completed.        PL/SQL procedure successfully completed.


PL/SQL procedure successfully completed.        PL/SQL procedure successfully completed.

SQL> @run_test                                  SQL> @run_test

INSTANCE_NUMBER                                 INSTANCE_NUMBER
---------------                                 ---------------
              2                                               1

+000000000 00:00:07.309916000                   +000000000 00:00:07.966913000

PL/SQL procedure successfully completed.        PL/SQL procedure successfully completed.

+000000000 00:00:08.430094000                   +000000000 00:00:07.341760000

PL/SQL procedure successfully completed.        PL/SQL procedure successfully completed.

alltså 7-8 sekunder för att välja 100 000 iterationer av sekvensen.

Låt oss nu prova NOCACHE (ORDER vs NOORDER är irrelavant för detta, eftersom vi tvingar en skrivning till seq$ för varje anrop till sekvensen).

SQL> alter sequence daz_test nocache;

Sequence altered.

SESSION 1                                       SESSION 2
SQL> @run_test                                  SQL> @run_test

INSTANCE_NUMBER                                 INSTANCE_NUMBER
---------------                                 ---------------
              2                                               1

+000000000 00:08:20.040064000                   +000000000 00:08:15.227200000

PL/SQL procedure successfully completed.        PL/SQL procedure successfully completed.

+000000000 00:08:30.140277000                   +000000000 00:08:35.063616000

PL/SQL procedure successfully completed.        PL/SQL procedure successfully completed.

så vi har hoppat från 8 sekunder till 8 MINUTTER för samma arbetsset.

hur är det med CACHE + BESTÄLLNING?

SQL> alter sequence daz_test cache 100 order;

Sequence altered.

SQL> @run_test                                  SQL> @run_test

INSTANCE_NUMBER                                 INSTANCE_NUMBER
---------------                                 ---------------
              2                                               1

+000000000 00:00:25.549392000                   +000000000 00:00:26.157107000

PL/SQL procedure successfully completed.        PL/SQL procedure successfully completed.

+000000000 00:00:26.057346000                   +000000000 00:00:25.919005000

PL/SQL procedure successfully completed.        PL/SQL procedure successfully completed.

så sammanfattningsvis för 100 000 enstaka samtal hämtasCACHE NOORDER =8 sekunderNOCACHE =8 minuterCACHE ORDER =25 sekunder

för cacheordning, oracle plingar mycket mellan RAC-noderna, men det GÖR INTE måste skriva tillbaka saker till seq$ tills cachestorleken är slut, eftersom allt är gjort i minnet.

Jag skulle om jag var du, ställ in en lämplig cachestorlek (p.s. en hög cachestorlek belastar inte lådans minne, eftersom Oracle inte lagrar alla siffror i RAM-minnet, bara det nuvarande + slutliga numret) och överväga BESTÄLL vid behov.




  1. Infoga text med enstaka citattecken i PostgreSQL

  2. Slinga på bord med PL/pgSQL i Postgres 9.0+

  3. Hur man returnerar ett inkrementellt gruppnummer per grupp i SQL

  4. Anslut bord från två olika servrar