rendimiento en la programacion abap

41
Introducción • Este documento es una compilación de distintas sentencias y procedimientos de programación en ABAP/4 relacionados con performance. Estas sentencias y procedimientos son comparados para determinar cuales tienen mejor performance. Los tiempos medidos para la ejecución no deben tomarse como valores absolutos sino como valores indicatiovos de comparación de performance. No pueden tomarse como valores de ejecución para una instalación determinada ya que fueron medidos en una server específico, con una carga de trabajo despreciable. • Además de las consideraciones sobre sentencias y procedimientos ABAP/4 se desarrollan puntos a tener en cuenta relacionados con la base de datos de SAP (vistas, índices, etc.). Interfaz SQL Select ... Where vs. Select + Check Select + Check Select sin condición SELECT * FROM VERI_CLNT CHECK: VERI_CLNT-ARG1 = ’7’. ENDSELECT. SELECT * FROM VERI_CLNT WHERE ARG1 = ’7’. ENDSELECT. 88,234 microsegundos 4,907 microsegundos • Siempre especifique sus condiciones en la cláusula WHERE en vez de realizar la evaluación de la condición con la instrucción check. • La base de datos entonces puede usar un índice ( si existe alguno adecuado ) siendo la performance de la red considerablemente mejor. Select single vs. Select-Endselect Select ... Endselect Select single * ... SELECT * FROM VERI_CLNT SELECT SINGLE * FROM VERI_CLNT

Upload: calderoman

Post on 21-Jun-2015

1.853 views

Category:

Documents


13 download

TRANSCRIPT

Page 1: Rendimiento en La Programacion ABAP

Introducción

• Este documento es una compilación de distintas sentencias y procedimientos de programación en ABAP/4 relacionados con performance. Estas sentencias y procedimientos son comparados para determinar cuales tienen mejor performance. Los tiempos medidos para la ejecución no deben tomarse como valores absolutos sino como valores indicatiovos de comparación de performance. No pueden tomarse como valores de ejecución para una instalación determinada ya que fueron medidos en una server específico, con una carga de trabajo despreciable.

• Además de las consideraciones sobre sentencias y procedimientos ABAP/4 se desarrollan puntos a tener en cuenta relacionados con la base de datos de SAP (vistas, índices, etc.).

Interfaz SQL

Select ... Where vs. Select + Check

Select + Check Select sin condición

SELECT * FROM VERI_CLNTCHECK: VERI_CLNT-ARG1 = ’7’.ENDSELECT.

SELECT * FROM VERI_CLNTWHERE ARG1 = ’7’.ENDSELECT.

88,234 microsegundos 4,907 microsegundos

• Siempre especifique sus condiciones en la cláusula WHERE en vez de realizar la evaluación de la condición con la instrucción check.

• La base de datos entonces puede usar un índice ( si existe alguno adecuado ) siendo la performance de la red considerablemente mejor.

Select single vs. Select-Endselect

Select ... Endselect Select single * ...

SELECT * FROM VERI_CLNTWHERE ARG1 = ’7’ ANDARG2 = ’ ’.ENDSELECT.

SELECT SINGLE * FROM VERI_CLNTWHERE ARG1 = ’7’ AND ARG2 = ’ ’.

4,549 microsegundos 4,160 microsegundos

• Si necesita una sola fila de una tabla de base de datos o vista, use la instrucción SELECT SINGLE en vez de un loop SELECT-ENDSELECT.

• SELECT SINGLE requiere una comunicación (I/O) con el sistema de la base de datos, mientras que SELECT-ENDSELECT necesita dos.

Page 2: Rendimiento en La Programacion ABAP

Funciones agregadas

Select ... Where + Check Select using una función agregada

C4A = ’000’.SELECT * FROM T100WHERE SPRSL = ’000’.CHECK: T100-MSGNR > C4A.C4A = T100-MSGNR.ENDSELECT.

SELECT MAX(MSGNR) FROM T100 INTO C4AWHERE SPRSL = ’D’ ANDARBGB = ’00’.

221,213 microsegundos 24,470 microsegundos

• Si requiere encontrar el valor máximo, mínimo, sumatoria y promedio o la cantidad de una columna de la base de datos; use las funciones agregadas en vez de agregar instrucciones para realizar el cálculo.

Select con Vistas

Instrucciones Select anidadas Select con vistas

SELECT * FROM DD01LWHERE DOMNAME LIKE ’CHAR%’ ANDAS4LOCAL = ’A’.SELECT SINGLE * FROM DD01T WHEREDOMNAME = DD01L-DOMNAME ANDAS4LOCAL = ’A’ ANDAS4SERVERS = DD01L-AS4VERS ANDDDLANGUAJE = SY-LANGU.ENDSELECT.

SELECT * FROM DD01VWHERE DOMNAME LIKE ’CHAR%’ ANDDDLANGUAJE = SY-LANGU.ENDSELECT.

1,472,996 microsegundos 308,670 microsegundos

• Para procesar un join, use una vista en vez de instrucciones Select anidadas.

Select con soporte de buffer

Select sin soporte de buffer Select con soporte de buffer

SELECT SINGLE * FROM T100BYPASSING BUFFERWHERE SPRSL = ’D’ ANDARBGB = ’00’ ANDMSGNR = ’999’.

SELECT SINGLE * FROM T100WHERE SPRSL = ’D’ ANDARBGB = ’00’ ANDMSGNR = ’999’.

4,395 microsegundos 242 microsegundos

Page 3: Rendimiento en La Programacion ABAP

• Para tablas de solo lectura y uso frecuente, utilice SAP buffering.

Actualización de columnas

Actualización de una línea por vez Actualización de las columnas

SELECT * FROM VERI_CLNT.VERI_CLNT-FUNCTINT =VERI_CLNT-FUNCTNT + 1.UPDATE VERI_CLNT.ENDSELECT.

UPDATE VERI_CLNTSET FUNCTINT = FUNCTINT + 1.

545,008 microsegundos 70,487 microsegundos

• Siempre que sea posible utilice la actualización por columnas, en vez de actualizar una línea de la tabla de la base de datos.

Select con soporte de índices

Select sin soporte de índices Select con soporte de índices

SELECT * FROM T100WHERE ARBGB = ’00’ ANDMSGNR = ’999’.ENDSELECT.

SELECT * FROM T002.SELECT * FROM T100WHERE SPRSL = T002-SPRAS ANDARBGB = ’00’ ANDMSGNR = ’999’.ENDSELECT.ENDSELECT.

3,749,142 microsegundos 121,096 microsegundos

• Para todo uso frecuente de la instrucción Select, trate de utilizar un índice. Siempre se usa un índice si se especifica una parte genérica de lo/s campos del índice, concatenándolos con AND lógicos en la cláusula WHERE.

Page 4: Rendimiento en La Programacion ABAP

Select ... Into Table t

Select + instrucción Append Select into table

REFRESH X006.SELECT * FROM T006 INTO TABLE X006.APPEND X006.ENDSELECT.

SELECT * FROM T006 INTO TABLE X006.

2,246 microsegundos 829 microsegundos

• Es siempre más rápido usar la instrucción Select into table que usar la instrucción Append.

Select-Endselect vs. Array-Select.

Select into Table t ... Loop at t Select ... Endselect.

SELECT * FROM T006 INTO TABLE X006.LOOP AT TABLE X006.ENDLOOP.

SELECT * FROM T006.ENDSELECT.

1,117 microsegundos 2,022 microsegundos

• Si procesa sus datos sólo una vez , use un SELECT-ENDSELECT-LOOP en vez de guardar los datos en una tabla interna con SELECT INTO TABLE. El manejo de una tabla interna consume más espacio.

Select with select list

Select * Select .with select list

SELECT * FROM DD01L WHEREDOMNAME LIKE ’CHAR%’ ANDAS4LOCAL = ’A’.ENDSELECT.

SELECT DOMNAME FROM DD01LINTO DD01L-DOMNAME WHEREDOMNAME LIKE ’CHAR%’ ANDAS4LOCAL = ’A’.ENDSELECT.

240,062 microsegundos 89,276 microsegundos

• Si sólo le interesan determinadas columnas de la tabla,use una lista de campos o una vista en vez de SELECT * .

Page 5: Rendimiento en La Programacion ABAP

Arrar Insert vs. Single-row Insert

Inserción de una línea por vez. Inserción con arreglos

* Tabla TAB con 100 entradasLOOP AT TAB.INSERT INTO VERI_CLNT VALUES TAB.ENDLOOP.

* Tabla TAB con 100 entradasINSERT VERI_CLNT FROM TABLE TAB.

463,581 microsegundos 53,917 microsegundos

• Siempre que sea posible, utilice operaciones con arreglos, en vez de operaciones sobre una fila.

• La frecuente comunicación entre el programa de aplicación y el sistema de la base de datos produce un considerable overhead.

Manipulación de strings

Operadores especiales en IF (CA,...)

Do-Loop con Field-Symbols Usando el operador CA

ASSIGN CHA(1) TO <C>.DO 200 TIMES.IF <C> = ’(’ OR <C> = ’)’." Alguna operación.EXIT.ENDIF.ASSIGN <C>+1 TO <C>.ENDDO.

IF CHA(200) CA ’()’." Alguna operación.ENDIF.

1,123 microsegundos 443 microsegundos

• Utilice los operadores especiales CO, CA, CS en vez de adicionar instrucciones de programación.

• Si se ejecutan instrucciones ABAP por cada caracter de un string, el consumo de CPU puede incrementarse substancialmente.

Page 6: Rendimiento en La Programacion ABAP

Concatenación de strings

Moviendo con offset Usando la instrucción CONCATENATE

MOVE ’Jane’ TO CMA.MOVE ’Miller’ TO CMB.MOVE ’New York City’ TO CMC.I1 = STRLEN(CMA). I2 = STRLEN(CMB).MOVE ’Mrs.’ TO CHA.MOVE CMA TO CHA+5. I1 = I1 + 6.MOVE CMB TO CHA+I1. I1 = I1 + 12 + 1.MOVE ’from’ TO CHA+I1. I1 = I1 + 11 + 5.MOVE CMC TO CHA+I1.

"Mrs. Jane Miller from New York City" es el valorfinal de CHA.

MOVE ’Jane’ TO CMA.MOVE ’Miller’ TO CMB.MOVE ’New York City’ TO CMC.

CONCATENATE’Mrs.’ CMA CMB ’from’ CMC INTO CHA SEPARATEBY SPACE.

"Mrs. Jane Miller from New York City" es el valorfinal de CHA.

93 microsegundos 28 microsegundos

• Utilice la instrucción CONCATENATE en vez de adicionar instrucciones de programación.

Borrando espacios en blanco

Corriendo SY-FDPOS lugares Usando SHIFT ... LEFT DELETING LEADING

" CLA contiene el string" ’ " Editor line n".

IF CLA CN SPACE. ENDIF.SHIFT CLA BY SY-FDPOS PLACES LEFT

" CLA contiene el string" ’ " Editor line n".

SHIFT CLA LEFT DELETING LEADING SPACE.

100 microsegundos 8 microsegundos

• Si quiere borrar los espacios en un string, utilice la instrucción SHIFT ... LEFT DELETING LEADING ...

• Otras instrucciones no tan rápidas:

• CN y SHIFT ... BY SY-FDPOS PLACES, con CONDENSE si es posible.

Page 7: Rendimiento en La Programacion ABAP

• CN y ASSIGN CLA+SY-FDPOS(LEN) ...

• Evite usar SHIFT dentro de un loop WHILE.

Concatenación de strings

Usando una función para concatenar Usando la instrucción CONCATENATE

CALL FUNCTION ’STRING_CONCATENATE_3’EXPORTINGSTRING1 = T100-ARBGBSTRING2 = T100-MSGNRSTRING3 = T100-TEXTIMPORTINGSTRING = CLAEXCEPTIONSTOO_SMALL = 01.

CONCATENATE T100-ARBGBT100-MSGNRT100-TEXT INTO CLA.

194 microsegundos 14 microsegundos

• Algunas funciones para el manejo de strings tienden a ser obsoletas y fueron reemplazadas por otras instrucciones o funciones en ABAP/4.

• STRING_CONCATENATE CONCATENATE

• STRING_SPLIT SPLIT

• STRING_LENGTH STRLEN()

• STRING_CENTERED WRITE ... TO ... CENTERED

• STRING_MOVE_RIGHT WRITE ... TO ... RIGHT-JUSTIFIED

Page 8: Rendimiento en La Programacion ABAP

Particiones de strings

Uso de SEARCH y MOVE con offset Uso de la instrucción SPLIT

CMA contiene ’(410)-45174-6654312’ y será divididoen Código de Area, Teléfono1 y Teléfono2

SEARCH CMA FOR ’-’.MOVE CMA(SY-FDPOS) TO AREA_CODE.I1 = SY-FDPOS + 2.

SEARCH CMA FOR ’-’ STARTING AT I1.I1 = I1 - 1.MOVE CMA+I1(SY-FDPOS) TO TEL_NO1.I1 = I1 + SY-FDPOS + 1.MOVE CMA+I1 TO TEL_NO2.

CMA contiene ’(410)-45174-6654312’ y será divididoen Código de Area, Teléfono1 y Teléfono2

SPLIT CMA AT ’-’ INTO AREA_CODETEL_NO1TEL_NO2.

66 microsegundos 11 microsegundos

• Utilice la instrucción SPLIT en vez de realizar una programación para dividir un string.

Longitud de strings

Obtener el CHECK_SUM con la longitud del campo

Obtener el CHECK_SUM con strlen()

DATA: BEGIN OF STR,LINE TYPE X, ENDOF STR,CHECK_SUM TYPE I.MOVE ’KALEBVPQDSCFG’ TO CLA.

DO 64 TIMES VAYING STR FROM CLANEXT CLA+1.CHECK STR NE SPACE.ADD STR-LINE TO CHECK_SUM.

ENDDO.

DATA: BEGIN OF STR,LINE TYPE X, ENDOF STR,CHECK_SUM TYPE I.MOVE ’KALEBVPQDSCFG’ TO CLA.

I1 = STRLEN(CLA).DO I1 TIME VARYING STR FROM CLA NEXTCLA+1.CHECK STR NE SPACE.ADD STR-LINE TO CHECK_SUMENDDO.

597 microsegundos 171 microsegundos

Page 9: Rendimiento en La Programacion ABAP

• Utilice la función STRLEN() para restringir la cantidad de ciclos que debe efectuar la instrucción DO, cuando determina un CHECK_SUM.

Tablas internas

Generando tablas ordenadas

Generación en un paso usando read/insert

Generación en dos pasos usando append y luego sort

TAB_DES contiene 1000 entradas

REFRESH TAB_DEST.LOOP AT TAB_SRC.READ TABLE TAB_DEST WITH KEYK = TAB_SRC-K BINARY SEARCH.INSERT TAB_SRC INTO TAB_DEST INDEXSY-TABIX.ENDLOOP.

TAB_DES contiene 1000 entradas

REFRESH TAB_DEST.LOOP AT TAB_SRC.APPEND TAB_SRC TO TAB_DEST.ENDLOOP.

SORT TAB_DEST BY K.

98,545 microsegundos 20,693 microsegundos

• Si la cantidad de líneas es pequeña, (menor a 20 entradas), o si se necesita acceder a la tabla interna mientras ésta es llenada; usar la opción READ/INSERT es la correcta.

• Si la cantidad de datos es grande y la tabla se usará sólo una vez que este llena, es preferible el proceso en dos pasos.

Generando tablas sin duplicados

Generación en un paso Generación en tres pasos

TAB_DES contiene 1000 entradas de las cuales 500son diferentes

REFRESH TAB_DEST.LOOP AT TAB_SRC.READ TABLE TAB_DEST WITH KEYK = TAB_SRC-K BINARY SEARCH.IF SY-SUBRC <> 0.INSERT TAB_SRC INTO TAB_DEST INDEXSY-TABIX.ENDIF.

TAB_DES contiene 1000 entradas de las cuales 500son diferentes

REFRESH TAB_DEST.LOOP AT TAB_SRC.APPEND TAB_SRC TO TAB_DEST.ENDLOOP.

SORT TAB_DEST BY K.DELETE ADJACENT DUPLICATES FROMTAB_DEST COMPARING K.

Page 10: Rendimiento en La Programacion ABAP

ENDLOOP.

43,469 microsegundos 26,259 microsegundos

• Si la cantidad de líneas es pequeña, (menor a 20 entradas), o si se necesita acceder a la tabla interna mientras ésta es llenada; usar la opción READ/INSERT es la correcta.

• Si la cantidad de datos es grande y la tabla se usará sólo una vez que este llena, es preferible el proceso en tres pasos.

Diferentes formas de acceso con clave

Acceso vía una clave default implícita Acceso vía una clave explícitamente asignada

Tabla TAB contiene 30 entradas de 500 bytes cada.La instrucción READ finaliza con SY-SUBRC=4

MOVE SPACE TO TAB.TAB-K = ’X’.READ TABLE TAB BINARY SEARCH.

Tabla TAB contiene 30 entradas de 500 bytes cada.La instrucción READ finaliza con SY-SUBRC=4

READ TABLE TAB WITH KEYK = ’X’ BINARY SEARCH.

37 microsegundos 15 microsegundos

• Si es posible, especifique el campo clave para realizar la lectura. De otra manera el campo clave tiene que ser calculado dinámicamente por el runtime system.

Clave de acceso para múltiple líneas

Clave de acceso con LOOP/CHECK Clave de acceso con LOOP … WHERE

Tabla TAB contiene 100 entradas de 500 bytes cada una, solo 5 coinciden con la clave de búsqueda.

LOOP AT TAB.CHECK TAB-K = KVAL." ...ENDLOOP.

Tabla TAB contiene 100 entradas de 500 bytes cada una, solo 5 coinciden con la clave de búsqueda.

LOOP AT TAB WHERE K = KVAL." ...ENDLOOP.

1,395 microsegundos 387 microsegundos

• LOOP … WHERE es más rápido que LOOP/CHECK porque LOOP … WHERE evalúa la condición específica internamente.

Page 11: Rendimiento en La Programacion ABAP

• Como todas las expresiónes lógicas, la performance es mejor si los operandos son del mismo tipo de datos. La performance puede ser incrementada si el LOOP … WHERE es combinado con FROM i1 and/or TO i2, si es posible.

Copiando tablas internas

Forma rudimentaria para copiar una tabla interna

 

Tabla TAB_SRC contiene 100 entradas de 100Bytes cada.

REFRESH TAB_DEST.LOOP AT TAB_SRC INTO TAB_DEST.APPEND TAB_DEST.ENDLOOP.

Tabla TAB_SRC contiene 100 entradas de 100 Bytes cada.

TAB_DEST[] = TAB_SRC[].

949 microsegundos 314 microsegundos

• Las tablas internas pueden ser copiadas por asignación igual que cualquier otro tipo de objetos de datos. Si la tabla interna itab tiene una línea de cabecera, la tabla puede accederse por itab[ ]

Ordenando tablas internas

SORT itab con una clave de ordenamiento por default

SORT itab con una clave específica

Tabla TAB contiene 100 entradas de 500 bytes cada una

SORT TAB.

Tabla TAB contiene 100 entradas de 500 bytes cada una

SORT TAB BY K.

2,026 microsegundos 821 microsegundos

• La ejecución sera más rápida si se especifica la mayor cantidad posible de claves de ordenamiento.

Page 12: Rendimiento en La Programacion ABAP

Loops Anidados

Loops anidados Loop de cursor paralelo

Tabla TAB1 contiene 100 entradas de 100 bytes cada unaTabla TAB2 contiene 10 * 100 = 1000 entradas de 100 bytes cada una

LOOP AT TAB1.LOOP AT TAB2 WHERE K = TAB1-K." ...ENDLOOP.ENDLOOP.

Tabla TAB1 contiene 100 entradas de 100 bytes cada unaTabla TAB2 contiene 10 * 100 = 1000 entradas de 100 bytes cada una

I2 = 1.LOOP AT TAB1.LOOP AT TAB2 FROM I2.IF TAB2-K <> TAB1-K.I2 = SY-TABIX.EXIT.ENDIF." ...ENDLOOP.ENDLOOP.

394,175 microsegundos 10,029 microsegundos

• Si TAB1 tiene n1 entradas y TAB2 tiene n2 entradas, el tiempo necesario para el loop anidado con el algoritmo directo es O(n1 * n2), cuando el cursor paralelo toma sólo O(n1 + n2). El algoritmo de cursor paralelo asume que TAB2 contiene sólo las entradas que también contiene en TAB1.

• Si esto no es cierto, el algoritmo de cursor paralelo se torna ligeramente más complicado, pero su característica de performance es la misma.

Borrando una secuencia de líneas

Rudimentaria forma para borrar una secuencia de líneas

Ordenando al kernel a realizar el trabajo

Tabla TAB_DEST contiene 1000 entradas 500 bytes cada una, las líneas 450 a 550 serán borradas.

DO 101 TIMES.DELETE TAB_DEST INDEX 450.ENDDO.

Tabla TAB_DEST contiene 1000 entradas 500 bytes cada una, las líneas 450 a 550 serán borradas.

DELETE TAB_DEST FROM 450 TO 550.

3,119 microsegundos 128 microsegundos

Page 13: Rendimiento en La Programacion ABAP

• Con la nueva variante del delete

DELETE itab FROM … TO …

la tarea de borrar una secuencia de líneas puede ser transferidas al kernel.

Generando tablas condensadas

COLLECT usando semántico READ BINARY

Juntando vía COLLECT

Tabla TAB_SRC contiene 10,000 entradas, 5,000de las cuales tiene diferente claves

LOOP AT TAB_SRC.READ TABLE TAB_DEST WITH KEYK = TAB_SRC-K BINARY SEARCH.IF SY-SUBRC = 0.ADD: TAB_SRC-VAL1 TOTAB_DEST-VAL1,TAB_SRC-VAL2 TOTAB_DEST-VAL2MODIFY TAB_DEST INDEX SY-TABIX.ELSE.INSERT TAB_SRC INTO TAB_DESTINDEX SY-TABIX.ENDIF.ENDLOOP.

Tabla TAB_SRC contiene 10,000 entradas, 5,000de las cuales tiene diferente claves

LOOP AT TAB_SRC.COLLECT TAB_SRC INTO TAB_DEST.ENDLOOP.SORT TAB_DEST BY K.

1,580,904 microsegundos 284,471 microsegundos

• Si necesita la semántica del COLLECT , use COLLECT!

• READ BINARY ejecuta en O(LOG2(n)) tiempo, y el índice de la tabla interna debe ser ajustado con cada INSERT. COLLECT, sin embargo, usa un algoritmo hash y es independiente del número de entradas i.e. O(1) y no necesita mantener una tabla de índices. Si necesita al final los datos ordenados, ordénelos después de que los datos han sido coleccionados.

• Si la cantidad de datos es pequeña, el acercamiento READ/INSERT no es malo, pero para cantidades mayores de datos (>1000), COLLECT es mucho más rápido.

• CUIDADO: cuando carga una tabla interna, no utilice COLLECT en combinación con alguna instrucción de carga de tablas, por ejemplo (APPEND, INSERT, and/or MODIFY). Si mezcla COLLECT con otra instrucción, COLLECT no puede usar su

Page 14: Rendimiento en La Programacion ABAP

algoritmo hash. En este caso COLLECTS ejecuta una búsqueda lineal, la cual es dramaticamente lenta: O(n).

Búsqueda Lineal vs. Binaria

Búsqueda Lineal Búsqueda Binaria

Tabla TAB contiene 1000 entradas de 100 bytescada. El READ finaliza con SY-SUBRC=4

READ TABLE TAB WITH KEY K = ’X’.

Tabla TAB contiene 1000 entradas de 100 bytescada. El READ finaliza con SY-SUBRC=4

READ TABLE TAB WITH KEYK = ’X’ BINARY SEARCH.

1,452 microsegundos 29 microsegundos

• Si la tabla interna tiene muchas (>20) entradas, en una búsqueda lineal a través de todas las entradas el tiempo consumido es bastante alto. Trate de mantener la tabla ordenada y usar búsqueda binaria.

• Si TAB tiene n entradas, la búsqueda lineal se ejecuta en O(n) de tiempo, mientras que la búsqueda binaria toma solamente O(log2(n)) de tiempo.

Índices secundarios

búsqueda linealSin índice secundario Búsqueda binaria usando índice secundario

Tabla TAB contiene 1000 entradas. El READ usa las 500 primeras entradas.

READ TABLE TAB WITH KEYDATE = SY-DATUM.IF SY-SUBRC = 0....ENDIF.

Tabla TAB contiene 1000 entradas. El READ usa las 500 primeras entradas.

READ TABLE TAB_INDEX WITH KEYDATE = SY-DATUM BINARY SEARCH.IF SY-SUBRC = 0.READ TABLE TAB INDEXTAB_INDEX-INDX....ENDIF.

798 microsegundos 32 microsegundos

• Si se necesita acceder a una tabla con diferentes claves repetidamente, mantenga su propio índice secundario.

• Con un índice secundario, puede remplazar una búsqueda lineal con una búsqueda binaria más un acceso indexado .

Page 15: Rendimiento en La Programacion ABAP
Page 16: Rendimiento en La Programacion ABAP

Usando un área explícita de trabajo

Operaciones con tablas vía la línea de cabecera

Operaciones con tablas vía una explícita área de trabajo

El ancho de la línea de la tabla TAB es 500 bytes

TAB = TAB_WA.APPEND TAB.

El ancho de la línea de la tabla TAB es 500 bytes

APPEND TAB_WA TO TAB.

17 microsegundos 9 microsegundos

• Evite los MOVEs innecesarios, usando las operaciones explícitas de áreas de trabajo.

• APPEND wa TO tab

• INSERT wa INTO tab

• COLLECT wa INTO tab

• MODIFY tab FROM wa

• READ tab INTO wa

• LOOP AT tab INTO wa cuando es apropiado.

Page 17: Rendimiento en La Programacion ABAP

Comparando tablas internas

Rudimentaria forma para comparar tablas internas

Ordenando al kernel a realizar el trabajo

Tablas TAB1 y TAB2 tienen cada 100 entradas de 100 Bytes cada

DESCRIBE TABLE: TAB1 LINES L1,TAB2 LINES L2.IF L1 <> L2.TAB_DIFFERENT = ’X’.ELSE.TAB_DIFFERENT = SPACELOOP AT TAB1.READ TABLE TAB2 INDEX SY-TABIX.IF TAB1 <> TAB2.TAB_DIFFERENT = ’X’. EXIT.ENDIF.ENDLOOP.ENDIF.IF TAB_DIFFERENT = SPACE." ...ENDIF.

Tablas TAB1 y TAB2 tienen cada 100 entradas de 100 Bytes cada

IF TAB1[] = TAB2[]." ...ENDIF.

1,774 microsegundos 535 microsegundos

• Una tabla interna puede ser comparada en una expresión lógica igual que otros objetos.

• Dos tablas internas son iguales si tienen el mismo numero de líneas y cada par de correspondiente línea es igual.

• Si una tabla interna itab tiene la línea de cabecera, la tabla en si misma es accedida por itab[].

Page 18: Rendimiento en La Programacion ABAP

Uniendo tablas internas

Join natural: loop tab1, read tab2 con clave

Cursor paralelo

Tabla TAB1 contiene 1000 entradas de 100 bytes cada una.Tabla TAB2 contiene 300 entradas de 100 bytes cada una.Tabla TAB2 se asume ordenada por K en orden ascendente

LOOP AT TAB1.READ TABLE TAB2 WITH KEYK = TAB1-K BINARY SEARCH.IF SY-SUBRC = 0....ENDIF.ENDLOOP.

Tabla TAB1 contiene 1000 entradas de 100 bytes cada una.Tabla TAB2 contiene 300 entradas de 100 bytes cada una.Tabla TAB2 se asume ordenada por K enorden ascendente

I2 = 1.LOOP AT TAB1.READ TABLE TAB2 INDEX I2.IF SY-SUBRC <> 0. EXIT. ENDIF.IF TAB2-K = TAB1-K." ...ADD 1 TO I2.ENDIF.ENDLOOP.

28,319 microsegundos 9,824 microsegundos

• Si TAB1 tiene n1 entradas y TAB2 tiene n2 entradas, el tiempo necesario para juntar TAB1 y TAB2 con el algoritmo directo es O(n1 * log2(n2)), mientras un acercamiento de cursor paralelo toma solamente O(n1 + n2) de tiempo.

• El mencionado algoritmo de cursor paralelo asume que TAB2 es un tabla secundaria conteniendo solo entradas también contenidas en la tabla primaria TAB1. Si esta asunción no es verdadera, el algoritmo de cursor paralelo es ligeramente más complicado, pero su performance restante es la misma.

Page 19: Rendimiento en La Programacion ABAP

Borrando duplicados

Rudimentaria forma de borrar duplicados Ordenado al kernel a realizar el trabajo

Tabla TAB_DEST contiene 1000 entradas de 100 bytes cada y contiene 500 pares de duplicados

READ TABLE TAB_DEST INDEX 1 INTO PREV_LINE.LOOP AT TAB_DEST FROM 2.IF TAB_DEST = PREV_LINE.DELETE TAB_DEST.ELSE.PREV_LINE = TAB_DEST.ENDIF.ENDLOOP.

Tabla TAB_DEST contiene 1000 entradas de 100 bytes cada y contiene 500 pares de duplicados

DELETE ADJACENT DUPLICATES FROM TAB_DEST COMPARING K.

26,826 microsegundos 4,159 microsegundos

• Con la nueva variante del DELETE , DELETE ADJACENT DUPLICATES, la tarea del borrado es transferida al kernel.

Borrando un conjunto de líneas

Rudimentaria forma de borrar un conjunto de líneas

Ordenado al kernel a realizar el trabajo

Tabla TAB_DEST contiene 1000 entradas de 500bytes cada, estas coinciden el WHERE condition

LOOP AT TAB_DEST WHERE K = KVAL.DELETE TAB_DEST.ENDLOOP.

Tabla TAB_DEST contiene 1000 entradas de 500bytes cada, estas coinciden el WHERE condition

DELETE TAB_DEST WHERE K = KVAL.

14,491 microsegundos 6,496 microsegundos

• Con la nueva variante del delete, DELETE itab [FROM … ] [TO … ] WHERE … , la tarea de borrar un conjunto de líneas puede ser transferido al kernel. Si es posible, WHERE debería ser usado junto con FROM … and/or TO para mejorar la performance aún más.

Page 20: Rendimiento en La Programacion ABAP

• La performance obtenida cuando se usa DELETE itab FROM, en vez de f LOOP AT itab WHERE … DELETE itab. ENDLOOP.mejora con el número de entradas de la tabla interna y el número de líneas a ser borradas.

WorkAreas vs Field-Symbols

Loop con WorkArea Loop con Field-Symbols

TYPES: BEGIN OF TY_DATA, VALUE TYPE STRING, END OF TY_DATA

Tabla TAB_INTERNA contiene 500000 entradas DATA: TAB_INTERNA STANDARD TABLE OF TY_DATA DATA: WA_TADA TYPE TY_DATA.

FIELD-SYMBOLS: <FS_DATA> LIKE LINE OF TAB_INTERNA.

DO 500000 TIMES. APPEND INITIAL LINE TO TAB_INTERNAL ASSIGNIGN <FS_DATA>. <FS_DATA>-VALUE = SY-INDEX ENDDO

LOOP AT TAB_INTERNA INTO WA_TAB. ENDLOOP.

TYPES: BEGIN OF TY_DATA, VALUE TYPE STRING, END OF TY_DATA

Tabla TAB_INTERNA contiene 500000 entradas DATA: TAB_INTERNA STANDARD TABLE OF TY_DATA FIELD-SYMBOLS: <FL> LIKE LINE OF TY_DATA.

FIELD-SYMBOLS: <FS_DATA> LIKE LINE OF TAB_INTERNA.

DO 500000 TIMES. APPEND INITIAL LINE TO TAB_INTERNAL ASSIGNIGN <FS_DATA>. <FS_DATA>-VALUE = SY-INDEX ENDDO

LOOP AT TAB_INTERNA ASSIGNING <FI>. ENDLOOP.

0,12 microsegundos 0,05 microsegundos

• En este ejemplo no se esta haciendo ningún cálculo, modificacion o impresion, que generaria mas tiempo, solo recorremos los registros, ademas si modificamos algn campo, con el field-symbols,la modificación es directa pero con la WorkArea habrai que mover los cambios a la tabla interna.

Page 21: Rendimiento en La Programacion ABAP

Tipos de datos

Tipos de datos declarados vs. parámetros sin declaración de tipo.

Parámetros sin definición de tipo Parámetros con definición de tipo

PERFORM UP1 USING IX M6-DIMIDM6-ZAEHL M6-ISOCODE M6-ANDECM6-PRIMARY.

FORM UP1 USINGREPEATDIMIDZAEHLISOCODEANDECPRIMARY.

Idéntico código fuente a la izquierda y derecha:

DO REPEAT TIMES.T006-DIMID = DIMID.T006-ZAEHL = ZAEHL.T006-ISOCODE = ISOCODE.T006-ANDEC = ANDEC.T006-PRIMARY = PRIMARY.I1 = REPEAT - SY-INDEX.ENDDO.ENDFORM.

PERFORM UP2 USING IX M6-DIMIDM6-ZAEHL M6-ISOCODE M6-ANDECM6-PRIMARY.

FORM UP2 USINGREPEAT TYPE IDIMID LIKE T006-DIMIDZAEHL LIKE T006-ZAEHLISOCODE LIKE T006-ISOCODEANDEC LIKE T006-ANDECPRIMARY LIKE T006-PRIMARY.

Idéntico código fuente a la izquierda y derecha:

DO REPEAT TIMES.T006-DIMID = DIMID.T006-ZAEHL = ZAEHL.T006-ISOCODE = ISOCODE.T006-ANDEC = ANDEC.T006-PRIMARY = PRIMARY.I1 = REPEAT - SY-INDEX.ENDDO.ENDFORM.

228 microsegundos 161 microsegundos

• Si especifica el tipo de dato a los parámetros en su código fuente, el compilador ABAP/4 puede optimizar el código completamente. Además el riesgo de usar una secuencia errónea de parámetros en una instrucción PERFORM es mucho menor.

• Si tiene una extensa cantidad de programas con declaraciones sin tipo, utilice la facilidad provista por el workbench para realizar una declaración de tipo automática.

Page 22: Rendimiento en La Programacion ABAP

Declaración de tipos vs. sin declaración de tipos en Field-symbols

Field-symbols sin tipo Ffield-symbols con declaración de tipo

FIELD-SYMBOLS: <F>.

ASSIGN I1 TO <F>.I2 = <F>.I3 = <F>.I4 = <F>.

FIELD-SYMBOLS: <I> type I.

ASSIGN I1 TO <I>.I2 = <I>.I3 = <I>.I4 = <I>.

11 microsegundos 7 microsegundos

• Si se especifica el tipo de datos del Field-symbols y de los parámetros en su código fuente, el compilador ABAP/4 puede optimizar mejor el código.

If vs. Case

If Case

IF C1A = ’A’. WRITE ’1’.ELSEIF C1A = ’B’. WRITE ’2’.ELSEIF C1A = ’C’. WRITE ’3’.ELSEIF C1A = ’D’. WRITE ’4’.ELSEIF C1A = ’E’. WRITE ’5’.ELSEIF C1A = ’F’. WRITE ’6’.ELSEIF C1A = ’G’. WRITE ’7’.ELSEIF C1A = ’H’. WRITE ’8’.ENDIF.

CASE C1A.WHEN ’A’. WRITE ’1’.WHEN ’B’. WRITE ’2’.WHEN ’C’. WRITE ’3’.WHEN ’D’. WRITE ’4’.WHEN ’E’. WRITE ’5’.WHEN ’F’. WRITE ’6’.WHEN ’G’. WRITE ’7’.WHEN ’H’. WRITE ’8’.ENDCASE.

16 microsegundos 7 microsegundos

• La instrucción CASE es clara y un poco más rápida que la construcción IF.

Page 23: Rendimiento en La Programacion ABAP

Case vs. Perform I of …

Case Perform I Of …

* (I1 = 5 in this test)CASE I1.WHEN 1. PERFORM PV1.WHEN 2. PERFORM PV2.WHEN 3. PERFORM PV3.WHEN 4. PERFORM PV4.WHEN 5. PERFORM PV5.WHEN 6. PERFORM PV6.WHEN 7. PERFORM PV7.WHEN 8. PERFORM PV8.ENDCASE.

* (I1 = 5 in this test)PERFORM I1 OFPV1PV2PV3PV4PV5PV6PV7PV8.

11 microsegundos 6 microsegundos

• Una forma rápida de llamar a una determinada rutinas usando un índice dado, es usar la instrucción PERFORM I OF … .

While vs. Do

Do Case

I1 = 0.DO.IF C1A NE SPACE. EXIT. ENDIF.ADD 1 TO I1.IF I1 GT 10. C1A = ’X’. ENDIF.ENDDO.

I1 = 0.WHILE C1A = SPACE.ADD 1 TO I1.IF I1 GT 10. C1A = ’X’. ENDIF.ENDWHILE.

8 microsegundos 6 microsegundos

• Si puede use WHILE en vez de una construcción DO+EXIT. WHILE es más fácil para entender y rápido para ejecutar.

Page 24: Rendimiento en La Programacion ABAP

Conversión de Campos

Campos tipos I y P

Tipo P Tipo I

DATA: IP TYPE P.DO 5 TIMES.IP = SY-INDEX * 2.READ TABLE X100 INDEX IP.ENDDO.

DATA: IP TYPE I.DO 5 TIMES.IP = SY-INDEX * 2.READ TABLE X100 INDEX IP.ENDDO.

78 microsegundos 37 microsegundos

• Es mejor usar campos de tipo I para variable que son tipicamente enteras tales como índices.

Constantes tipo F

Literal tipo C Constantes tipo F

DATA:FLOAT TYPE F.

FLOAT = ’3.1415926535897932’.

CONSTANTS:PI TYPE F VALUE ’3.1415926535897932’.

DATA:FLOAT TYPE F.

FLOAT = PI.

22 microsegundo 1 microsegundo

• Usar correctamente las constantes declaradas en vez de literales.

Mezcla de tipos

Varios tipos Unicamente 1 tipo

DATA: F1 TYPE I VALUE 2,F2 TYPE P DECIMALS 2 VALUE ’3.14’,F3 TYPE F.

F3 = F1 * F2.

DATA: F1 TYPE F VALUE 2,F2 TYPE F VALUE ’3.14’,F3 TYPE F.

F3 = F1 * F2.

46 microsegundos 1 microsegundos

• No mezcle tipos a menos que sea absolutamente necesario.

Page 25: Rendimiento en La Programacion ABAP

Literales tipo C y tipo I

Tipo C Tipo I

SY-SUBRC = ’0’.CASE SY-SUBRC.WHEN ’1’.WHEN ’2’.WHEN ’3’.WHEN ’4’.ENDCASE.

SY-SUBRC = ’0’.CASE SY-SUBRC.WHEN ’1’.WHEN ’2’.WHEN ’3’.WHEN ’4’.ENDCASE.

14 microsegundos 6 microsegundos

• Utilice literales numéricos o constantes con un tipo de número en vez de un string de caracteres, si son tratados como enteros o campos tipo P.

Aritmética

Tipo N Tipo P

DATA:N1(15) TYPE N VALUE ’123456789012345’,N2(15) TYPE N VALUE ’543210987654321’,N3(15) TYPE N.

N3 = N1 + N2.

DATA:P1 TYPE P VALUE ’123456789012345’,P2 TYPE P VALUE ’543210987654321’,P3 TYPE P.

P3 = P1 + P2.

29 microsegundos 8 microsegundos

• Utilice tipos numéricos para operaciones aritméticas.

Page 26: Rendimiento en La Programacion ABAP

UTILIZACIÓN DE TABLAS TRANSPARENTES, POOL Y CLUSTERS

Tablas Transparentes y Pool

Cuando seleccione desde una tabla Transparente o Pool, siempre restrinja la sentencia SELECT los más posible con la opción WHERE. También con campos de datos que pueden no ser parte de la clave. Esto permite a la Base de Datos evaluar los registros y devolver solamente aquellos que concuerdan con el criterio de selección.

Tablas transparentes y pool:

Select + Check Select ... Where

SELECT * FROM ZZLT2WHERERLDNR = V_LDGRANDRRCTY = ’0’ANDRVERS = ’001’ANDRYEAR = V_YR.CHECK V_CMPNY.CHECK V_ACCT.CHECK V_CNTR.………ENDSELECT.

SELECT * FROM ZZLT2WHERERLDNR = V_LDGRANDRRCTY = ’0’ANDRVERS = ’001’ANDRYEAR = V_YRANDBUKRS = V_CMPNYANDRACCT = V_ACCTANDRCNTR = V_CNTR.…….ENDSELECT

Requiere más memoria y buffer Mas eficientex

Tablas Cluster

Cuando trabaje con tablas cluster hay que hacer exactamente lo contrario del punto anterior. Solo utilice el comando SELECT, con los campos que son parte de la clave. Si la tabla es una Tabla Cluster se usa el comando CHECK para eliminar registros después que la selección fue acotada usando la cláusula WHERE con campos clave.

Las tablas clusters no pueden ser procesadas por la base de datos directamente, las tablas transparentes si. En la mayoría de los casos forzar a la base de datos a abrir y chequear los campos (como cuando se usa SELECT y WHERE sobre campos no clave) es menos eficiente que utilizar solo campos clave en el WHERE y permitir que ABAP verifique los campos no clave después que los datos son devueltos.

Page 27: Rendimiento en La Programacion ABAP

Tablas Cluster:

Para tablas Cluster BSEG con claves MANDT, BUKRS, BELNR, GJAHR, y BUZEI:

Select ... Where Select + Check

SELECT * FROM BSEGWHERE BELNR = BSIK-BELNRANDBUKRS = BSIK-BUKRSANDLIFNR = BSIK-LIFNRANDSHKZG = ’S’ANDKOART = ’K’.……..ENDSELECT.

SELECT * FROM BSEGWHERE BUKRS = BSIK-BUKRSANDREBZG = BSIK-BELNR.CHECK BSIK-LIFNR = BSEG-LIFNR.CHECK BSEG-SHKZG = ’S’.CHECK BSEG-KOART = ’K’.……..ENDSELECT.

Trabajará pero requiere mucha memoria disponible, espacio de Buffer y tiempo de base de datos para desempaquetar y comparar datos. Este trabajo puede ser muy costoso. Puede cargar excesivamente el servidor de base de datos

Trabajará más eficazmente con tablas cluster, especialmente en ambientes de muchos servidores de aplicación.

Atributos de los campos en el WHERE

Los campos que se comparan en el WHERE deben tener atributos similares. Si no los tienen el sistema debe convertirlos cada vez que se realice la comparación. Cuando no se los pueda hacer similares a travéz de la definición de los campos, se deben mover los datos a campos de trabajo antes de hacer la comparación.

Por ejemplo : SELECT * FROM ZZLT2 WHERE RLDNR = LDGR AND RRCTY = ’0’ AND RVERS = ’001’ AND RYEAR = YEAR.

    SELECT * FROM ZZLS2     WHERE RLDNR = ZZLT2-RLDNR     AND RRCTY = ZZLT2-RRCTY     AND BUKRS = ZZLT2-BUKRS.

Page 28: Rendimiento en La Programacion ABAP

      SELECT * FROM BSEG       WHERE BUKRS = ZZLS2-BUKRS       AND BELNR = ZZLS2-DOCNR       AND GJAHR = ZZLS2-RYEAR

      AND BUZEI = ZZLS2-DOCLN.

==> Compara un NUMC 3 con un CHAR 3. Dado que este SELECT se va a ejecutar muchas veces, sería más eficiente mover el campo de datos antes de comenzar el loop del SELECT.

DATA: ZZ_TEMP_DOCLN LIKE BESG-BUZEI. . . . SELECT * FROM ZZLT2 WHERE RLDNR = LDGR AND RRCTY = ’0’ AND RVERS = ’001’ AND RYEAR = YEAR.

    SELECT * FROM ZZLS2     WHERE RLDNR = ZZLT2-RLDNR     AND RRCTY = ZZLT2-RRCTY     AND BUKRS = ZZLT2-BUKRS.

    MOVE ZZLS2-DOCLN TO ZZ_TEMP_DOCLN.

      SELECT * FROM BSEG       WHERE BUKRS = ZZLS2-BUKRS       AND BELNR = ZZLS2-DOCNR       AND GJAHR = ZZLS2-RYEAR       AND BUZEI = ZZ_TEMP_DOCLN.

Page 29: Rendimiento en La Programacion ABAP

Generación de índices secundarios

• Toda tabla SAP tiene un índice primario, que consiste de los campos claves que el usuario definió en el proceso de creación de la tabla. El índice puede no ser utilizado si no se tienen todas las claves en la cáausula WHERE del SELECT o si la cláusula WHERE no es correctamente especificada. En este caso el administrador de la base de lee toda la tabla.

• El diccionario de datos de SAP soporta un máximo de 16 índices por cada tabla.

• Los índices deberían, generalmente, tener menos de cinco campos.

• Los campos más selectivos de la tabla deberían estar primeros en el índice (por ejemplo el campo MANDT en casi todas las tablas).

• En general si una condición incluye el operador OR, el optimizador detiene su procesamiento ( e invoca una búsqueda completa de la tabla ) tan pronto como es encontrado el primer OR. La posible excepción es un OR que proponga una separada y única condición para la evaluación.

Por Ejemplo :

La tabla ZTABLE se define con el siguiente índice.     Nombre del campo Tipo Longitud     FIELDC   CHAR   3     FIELDF   CHAR   3

SELECT * FROM ZTABLE WHEREFIELDC = ’ABC’ AND( FIELDF = ’12’ OR FIELDF = ’13’)

SELECT * FROM ZTABLE WHERE( FIELDC = ’ABC’ AND FIELDF = ’12’ ) OR( FIELDC = ’ABC’ AND FIELDF = ’13’)

No será utilizado el índice secundario El índice será utilizado como se esperaba

• Las cláusulas IN frecuentemente se interpretan igual que las OR y pueden llevar al mismo problema del punto anterior.

• La creación de índices adicionales bajará la performance en las funciones de inserción de registros en la tabla. En general esto tiene un impacto alto si existen muchos índices sobre la misma tabla.

• Un campo de un índice es válido solo si todos los campos que lo preceden son utilizados en el WHERE del SELECT.

Page 30: Rendimiento en La Programacion ABAP

Por Ejemplo :

La tabla ZTABLE se define con el siguiente índice.     Nombre del campo Tipo Longitud     FIELDA   CHAR   3     FIELDB   CHAR   3     FIELDC   CHAR   2

SELECT * FROM ZTABLEWHERE FIELDA = ’ABC’AND FIELDB = ’XYZ’AND FIELDD = ’DEFG’.

SELECT * FROM ZTABLEWHERE FIELDA = ’ABC’AND FIELDB = ’XYZ’AND FIELDC = ’12’.

No será utilizado el índice secundario El índice será utilizado como se esperaba

Enlaces

ABAP Fine Tuning http://www.sap-img.com/abap/abap-fine-tuning.htm Use of FOR ALL ENTRIES

http://www.thespot4sap.com/articles/SAPABAPPerformanceTuning_ForAllEntries.asp

WorkAreas vs Field-Symbols http://atejada.blogspot.com/2008/01/workarea-vs-field-symbols.html