Oracle - pl/sql - rendimiento de bucles - loop performance

Carlos Garcia publica un post en el blog de Innova acerca de las diferencias de tiempo que obtiene al hacer el mismo número de iteraciones dentro de un bucle. Yo hice la prueba de rendimiento con diferentes formas de bucles, el mismo número de iteraciones y a poder ser el mismo código a ejecutar, que será básicamente un contador:


DECLARE
    i       NUMBER := 0;
    j       NUMBER := 0;
    b       BOOLEAN := FALSE;
    i_begin INTEGER;
    n_limit CONSTANT NUMBER := 100000000;
BEGIN
    i_begin := DBMS_UTILITY.GET_TIME;
    j := 0;
    FOR i IN 0..n_limit
    LOOP
        j := j + 1;
    END LOOP;
    DBMS_OUTPUT.PUT_LINE (
           TO_CHAR((DBMS_UTILITY.GET_TIME - i_begin)/100)
        || '  FOR'
    );
    --
    i_begin := DBMS_UTILITY.GET_TIME;
    j := 0;
    LOOP
        j := j + 1;
        EXIT WHEN j = n_limit;
    END LOOP;
    DBMS_OUTPUT.PUT_LINE (
           TO_CHAR((DBMS_UTILITY.GET_TIME - i_begin)/100)
        || '  LOOP EXIT WHEN'
    );
    --
    i_begin := DBMS_UTILITY.GET_TIME;
    j := 0;
    LOOP
        j := j + 1;
        IF j = n_limit
        THEN
            EXIT;
        END IF;
    END LOOP;
    DBMS_OUTPUT.PUT_LINE (
           TO_CHAR((DBMS_UTILITY.GET_TIME - i_begin)/100)
        || '  LOOP IF EXIT'
    );
    --
    i_begin := DBMS_UTILITY.GET_TIME;
    j := 0;
    WHILE TRUE
    LOOP
        j := j + 1;
        EXIT WHEN j = n_limit;
    END LOOP;
    DBMS_OUTPUT.PUT_LINE (
           TO_CHAR((DBMS_UTILITY.GET_TIME - i_begin)/100)
        || '  WHILE TRUE EXIT WHEN'
    );
    --
    i_begin := DBMS_UTILITY.GET_TIME;
    j := 0;
    WHILE j < n_limit + 1
    LOOP
        j := j + 1;
    END LOOP;
    DBMS_OUTPUT.PUT_LINE (
           TO_CHAR((DBMS_UTILITY.GET_TIME - i_begin)/100)
        || '  WHILE LOOP'
    );
    --
    i_begin := DBMS_UTILITY.GET_TIME;
    j := 0;
    WHILE b = FALSE
    LOOP
        j := j + 1;
        IF j = n_limit
        THEN
            b := TRUE;
        END IF;
    END LOOP;
    DBMS_OUTPUT.PUT_LINE (
           TO_CHAR((DBMS_UTILITY.GET_TIME - i_begin)/100)
        || '  WHILE LOOP IF THEN'
    );
END;

Se obtiene como resultado (en segundos):

10,48  FOR
12,58  LOOP EXIT WHEN
12,59  LOOP IF EXIT
12,61  WHILE TRUE EXIT WHEN
13,11  WHILE LOOP
16,61  WHILE LOOP IF THEN

el WHILE como se puede ver es el más lento de ejecutar, de todas maneras si el código que vas a ejecutar son sentencias DML yo hago lo que recomienda ORACLE y es utilizar el FORALL que es incluso más eficiente que el FOR.

11 Tuning PL/SQL Applications for Performance
http://www.stanford.edu/dept/itss/docs/oracle/10g/
appdev.101/b10807/12_tune.htm

Via:
http://www.balearsinnovacio.com/blog/?p=490

Sin comentarios

No comments yet

Leave a reply