Está en la página 1de 9

INDEX

Un índice es una estructura de disco asociada con una tabla o una vista que acelera la
recuperación de filas de la tabla o de la vista. Un índice contiene claves generadas a partir de una o
varias columnas de la tabla o la vista. Dichas claves están almacenadas en una estructura (árbol b)
que permite buscar de forma rápida y eficiente la fila o filas asociadas a los valores de cada clave.
[ CITATION Jos04 \l 9226 ]

Un índice es como una tabla auxiliar que sólo contiene ciertas columnas de búsqueda. Por
eso también es posible (y recomendable) indicar el tablespace en el cual se almacenará.

Oracle recomienda que los índices residan en un tablespace y datafile separado al de las
tablas ya que dos tablespaces distintos pueden están almacenados físicamente por, al
menos, un datafile cada uno. Si nuestro servidor de base de datos tiene más de un disco
duro (algo muy normal), es posible crear un tablespace con sus datafiles en un disco y otro
tablespace con los datafiles en otro disco. Esto permite que se puedan hacer lecturas de
disco simultáneamente sobre dos disco físicos, ya que cada disco tiene su propio bus de
datos. Al crear los índices en un disco físico y los datos en otro, se facilita que se puedan
hacer lecturas simultaneas.
Este proceso (de poner los índices y datos en discos separados), se denomina balanceado.

Oracle crea automáticamente un índice cuando se define la clave primaria. Esto es debido
a que la condición más habitual en una consulta a cualquier tabla es a través de los
campos de su clave primaria. De esta forma se aceleran la gran mayoría de las consultas
(recordar que el índice de una tabla actúa del mismo modo que el de un libro).

Pero pueden darse casos en los que se hagan gran cantidad de consultas por campos
distintos a los de la clave primaria. En este caso es necesario crear un índice por los
campos por lo que se accede.

Sintaxis

CREATE {UNIQUE} INDEX nombre_índice


ON tabla( columnas_indexadas )
{TABLESPACE tab_indices}
{STORAGE( INITIAL XX{K|M} NEXT XX{K|M} )}

La cláusula UNIQUE actúa como si los campos indexados fuesen clave primaria, es decir,
no permite que el conjunto de campos indexados se repita en la tabla.

Por ejemplo, puede ser que en nuestra tabla FACTURA sea muy común recuperar aquellas
facturas de un cierto cliente.
En este caso la consulta SELECT ha realizar sería la siguiente:
SELECT *
FROM FACTURA
WHERE C_PAIS = 1 AND
C_CLIENTE = ‘A111’;

En este caso se está accediendo la tabla FACTURA por campos distintos a la clave primaria
(que es Referencia). Si este tipo de consultas son muy habituales es necesario crear un
índice por estos campos:

CREATE INDEX ind_factura_cliente


ON FACTURA( C_PAIS, C_CLIENTE )
TABLESPACE tab_factura_ind
STORAGE( INITIAL 500K NEXT 500K );

No podemos poner la cláusula UNIQUE porque si no, no podríamos insertar más de una
factura por cliente.

Ventajas de los Índices

 Una de las mayores ventajas es que cuando un SGBD se encuentra un índice evitamos
un “escaneo completo de la tabla” lo que hace que cuando tenemos grandes
cantidades de datos en nuestras tablas, la mejora puede ser muy importante.
 Muy relacionado con el anterior, al evitar “escaneos completos de las tablas”,
evitamos los siguientes problemas: Sobrecarga de CPU, sobrecarga de disco y
concurrencia.
 Con los índices evitamos que un SGBD tenga que hacer lecturas secuenciales.
 Los índices nos permiten una mayor rapidez en la ejecución de las consultas tipo
SELECT
 Será una ventaja para aquellos campos que no tengan datos duplicados, sin embargo
si es un campo con valores que se repiten continuamente (Ej. Masculino/Femenino) no
es aconsejable.

Desventajas de los Índices

Pero a pesar de sus grandes ventajas no debemos abusar de ellos puesto que en
determinadas situaciones no supondrá una mejora:

 Los índices son una desventaja en aquellas tablas las que se utiliza frecuentemente
operaciones de escritura (Insert, Delete, Update), esto es porque los índices se
actualizan cada vez que se modifica una columna.
 Los índices también suponen una desventaja en tablas demasiado pequeñas puesto
que no necesitaremos ganar tiempo en las consultas.
 Tampoco son muy aconsejables cuando pretendemos que la tabla sobre la que se
aplica devuelva una gran cantidad de datos en cada consulta.
 Hay que tener en cuenta que ocupan espacio y en determinadas ocasiones incluso más
espacio que los propios datos.

Estructura de un índice B-tree

Este tipo se estructura como un árbol cuya raíz contiene múltiples entradas y valores de
claves que apuntan al siguiente nivel del árbol. Cada una de estas entradas mantienen un
orden sobre las claves que están siendo almacenadas de forma tal que el apuntador a la
izquierda de una clave C indicara la el bloque de nivel siguiente en el árbol donde se
ubican claves menores que C. De igual forma, el apuntador a la derecha de una clave C´
indicara la el bloque de nivel siguiente en el árbol donde se ubican claves mayores que C´.
Todos los nodos internos del árbol tienen la misma estructura. Los nodos hoja contienen
la entrada del índice con toda la información necesaria para localizar la(s) fila(s) que
contienen un valor específico para la clave. Los nodos hoja se encuentran doblemente
enlazados para facilitar el recorrido del índice en orden ascendente o descendente. Cada
entrada en un nodo hoja representará las filas que posee el mismo valor para la clave y
posee la siguiente estructura:

 Un encabezado que almacena el número de columnas e información sobre el uso


concurrente de la fila.
 Una secuencia de valores de longitud de columna y valor de columna que permiten
expresar el valor de la clave almacenada en dicha entrada.
 El ROWID de la fila que posee el valor de la clave.
En la figura anterior se puede observar que a la izquierda del nodo principal se encuentran los
valores de clave menores que 5000 y a la derecha los mayores de 5000.

Es importante recordar que en las hojas del árbol se encuentra las filas que tienen el mismo valor
clave junto con su rowid, el cual identifica la posición de lectura de cada registro
Estructura de un índice Bitmap

Un índice bitmap también está organizado como un B*-Tree, pero la estructura de los nodos
hoja cambia para almacenar un bitmap definido sobre los valores de la clave en lugar de ROWIDs.
Cada bit en el bitmap corresponde a un posible ROWID, y si el bit está encendido esto significa que
el ROWID en cuestión posee el valor indicado para la clave. ORACLE almacena de forma
comprimida los “bitmap” asociados a cada entrada del índice utilizando para tal fin una técnica
propietaria

INDICES B-TREE VS BITMAP

 Los índices de tipo bitmap son particularmente eficientes cuando el universo de valores
posibles para las columnas del índice tiene una baja cardinalidad. Al existir un gran universo de
posibles valores para la columna aumenta el número de posibles claves y adicionalmente el
tamaño de los bitmaps a ser mantenidos en las entradas del índice. Enescenarios donde el
universo de valores de las claves es muy grande, los índices basados en B*-Tree son más
adecuados que los índices bitmap.
 Los índices de tipo bitmap son particularmente idóneos en escenarios en los que no se
producen o se producen muy pocas actualizaciones sobre las columnas que conforman la
clave. Una actualización en una de estas columnas trae implícita la modificación de dos o más
entradas del índice (incluidos los bitmaps). De igual forma, la inserción de un nuevo valor de la
clave trae implícita una reorganización masiva del índice, la cual es extremadamente costosa.
 Los índices de tipo bitmap permiten acelerar más consultas que utilicen el operador de
disyunción sobre los atributos claves. Verificar si el valor de una columna de la clave está entre
un grupo de valores es sencillo en un índice bitmap ya que sólo debe efectuarse el OR bit a bit
de los bitmaps asociados a las entradas de los valores en el rango de búsqueda. En los índices
basados en B*-Trees esta operación es más costosa.
 Como regla general, los índices basados en B*-Tree son mejores para ambientes de
procesamiento de transacciones en línea (OLTP – On-Line Transaction Processing), en los que
suelen existir tablas de alta volatilidad (gran número de operaciones de inserción y
eliminación) y de alta frecuencia de actualización. Por otra parte los índices bitmap son muy
útiles en ambientes donde se realizan consultas muy complejas sobre tablas muy poco
volátiles y que prácticamente no sufren actualizaciones. Ambientes de este tipo son los
derivados del uso de técnicas de “Data Warehousing” o en Sistemas de soporte a la decisión
(DSS – Decisión Support Systems).

OPTIMIZACION DE CONSULTAS

Tenga en cuenta los siguientes consejos:

EN LA CREACIÓN DE TABLAS:

 Normaliza las tablas, al menos hasta la tercera forma normal, para asegurar que no hay
duplicidad de datos y se aprovecha al máximo el almacenamiento en las tablas. Si hay que
desnormalizar alguna tabla piensa en la ocupación y en el rendimiento antes de proceder.
 Los primeros campos de cada tabla deben ser aquellos campos requeridos y dentro de los
requeridos primero se definen los de longitud fija y después los de longitud variable.
 Ajusta al máximo el tamaño de los campos para no desperdiciar espacio.
 Es muy habitual dejar un campo de texto para observaciones en las tablas. Si este campo se va
a utilizar con poca frecuencia o si se ha definido con gran tamaño, por si acaso, es mejor crear
una nueva tabla que contenga la clave primaria de la primera y el campo para observaciones.
 Una PK de tamaño pequeño es mucho más eficiente para el proceso de recuperación de filas
que una de tamaño grande.

EN LA PROYECCIÓN DE CAMPOS

 Seleccionar exclusivamente aquellos que se necesiten


 No utilizar nunca SELECT * porque el gestor debe leer primero la estructura de la tabla antes
de ejecutar la sentencia
 Si utilizas varias tablas en la consulta especifica siempre a que tabla pertenece cada campo, le
ahorras al gestor el tiempo de localizar a que tabla pertenece el campo. En lugar de SELECT
Nombre, Factura FROM Cliente join Factura on IdCliente = IdClienteFacturado; usa: SELECT
Clientes.Nombre, Facturacion.Factura from Cliente join Factura on Clientes.IdCliente =
Facturacion.IdClienteFacturado.

EN EL WHERE

 Seleccionar o comparar siempre por campos que sean claves o índices.


 Si deseamos interrogar por campos pertenecientes a índices compuestos es mejor
utilizar todos los campos de todos los índices. Supongamos que tenemos un índice
formado por el campo NOMBRE y el campo APELLIDO y otro índice formado por el campo
EDAD. La sentencia WHERE NOMBRE='Juan' AND APELLIDO Like '%' AND EDAD = 20
sería más óptima que WHERE NOMBRE = 'Juan' AND EDAD = 20 por que el gestor, en
este segundo caso, no puede usar el primer índice y ambas sentencias son equivalentes
por que la condición APELLIDO Like '%' devolvería todos los registros.
 Utilizar lo menos posible ANY, SOME, EXISTS, IN (SELECT Campo1 From Tabla2)
 Si va a utilizar en el where campos que son indexados, utilizarlos en el mismo orden en
el cual fue creado el índice, es decir, si un índice se creó (ciudad, fecha), utilizarlos en
ese orden en el where, ya que si lo hace en otro orden la ventaja de los índices
desaparece.
 Si se tiene una subconsulta pesada, es preferible utilizar Exists que In

EN JOINS

 Utilizar Inner Join , left join , right join, para unir las tablas en lugar del where, esto permite
que a medida que se declaran las tablas se vallan uniendo mientras que si utilizamos el
where el motor genera primero el producto cartesiano de todos los registros de las tablas
para luego filtrar las correctas, un trabajo definitivamente lento
 En consultas en las cuales se hayan incluido dos tablas, se tiene que estar seguro de que
los campos por los cuales estamos realizando al unión entre ambas tablas, están
indexados. Cuando unimos dos tablas se debe buscar por aquellos registros los cuales
tengan el mismo valor en el campo que une ambas tablas, será mucho más eficiente
buscar en los índices para localizar los registros que cumplen el criterio que tener que
buscar en ambas tablas y localizar los registros.
 El orden de ubicación las tablas en el from deberían ir en lo preferible de menor a mayor
según el número de registros , de esta manera reducimos la cantidad de revisiones de
registros que realiza el motor al unir las tablas a medida que se agregan.
 Si se tiene una tabla con muchos registros repetidos, es preferible utilizar una subconsulta
en el from que incluya el distinct, o un where donde se eliminen los registros inecesarios.

MANEJO ADECUADO DE LOS ÍNDICES

 El uso de los índices en una aplicación tiene una doble vertiente, lo cual en ciertas situaciones
puede ser provechosa mientras que en otras situaciones puede no serlo tanto.

 Los índices son campos elegidos arbitrariamente por el constructor de la base de datos que
permiten la búsqueda a partir de dicho campo a una velocidad notablemente superior. Sin
embargo, esta ventaja se ve contrarrestada por el hecho de ocupar mucha más memoria (el
doble más o menos) y de requerir para su inserción y actualización un tiempo de proceso
superior.

 Se debe tener en cuenta que cuando se crea un índice se está introduciendo una cantidad de
información la cual será útil a la hora de que el motor de la base de datos lea la información de
las tablas de la base de datos; pero esa información se tendrá que actualizar cuando la
información en las tablas se modifique o actualice, para que en posteriores lecturas el acceso
sea el adecuado.

 Evidentemente, no podemos indexar todos los campos de una tabla extensa ya que doblamos
el tamaño de la base de datos. Igualmente, tampoco sirve de mucho el indexar todos los
campos en una tabla pequeña ya que las selecciones pueden efectuarse rápidamente de todos
modos.

 Los índices pueden resultar contraproducentes si los introducimos sobre campos triviales a
partir de los cuales no se realiza ningún tipo de petición ya que, además del problema de
memoria ya mencionado, estamos ralentizando otras tareas de la base de datos como son la
edición, inserción y borrado. Es por ello que vale la pena pensárselo dos veces antes de
indexar un campo que no sirve de criterio para búsquedas o que es usado con muy poca
frecuencia por razones de mantenimiento.

 Con ello tenemos que tener en cuenta que en aquellas aplicaciones donde sólo se van a
realizar consultas, sistemas de ayuda a la decisión, es mejor tener la base de datos muy
indexada mientras que en aplicaciones las cuales requieren actualizaciones de cantidades
importantes de información sistemas transaccionales sería conveniente no tener la base de
datos muy indexada.

 En resumen; normalmente los campos que se recomiendan indexar son:


 Claves Primarias
 Claves Foráneas
 Campos por los cuales se realizaran búsquedas
 Campos por los cuales se va a ordenar

EN LAS APLICACIONES:
 En la medida de lo posible hay que evitar que las sentencias SQL estén embebidas dentro del
código de la aplicación. Es mucho más eficaz usar vistas o procedimientos almacenados por
que el gestor los guarda compilados. Si se trata de una sentencia embebida el gestor debe
compilarla antes de ejecutarla.

PLAN DE EJECUCION DE UNA CONSULTA

Cuando Oracle ejecuta una consulta crea un plan de ejecución, el cual define como resolver la
petición SQL, este plan sirve de base para realizar el análisis de una consulta y saber dónde
optimizar o comparar cual consulta es mejor, ya que a través del plan se puede saber el costo de
CPU, cantidad de filas que se debe procesar, memoria que se utiliza, cardinalidad de cada tabla.

Para consultar el plan de una consulta primero se debe crear:

explain plan [SET STATEMENT_ID = 'texto'] for consulta

ejemplo
explain plan for
select * from (employees join departments on employees.department_id=
departments.department_id) left join job_history on
employees.employee_id=job_history.employee_id;

SET STATEMENT_ID permite asignarle un nombre al plan, de tal manera que podamos
identificarlo, ya que todos los planes de ejecución se guardan por defecto en la tabla PLAN_TABLE.

Para consultar el plan de ejecución se utiliza la siguiente instrucción:


SELECT * FROM PLAN_TABLE ;

Si desea eliminar los planes creados ejecute:


Delete PLAN_TABLE

Para entender cómo interpretar el plan de ejecución remítase a:


http://fridafabiolah.galeon.com/explain_plan_oracle.htm l

PRACTICA

De acuerdo a este documento optimice las siguientes consultas, y para cada una de ellas explique
el plan de ejecución, comparando el plan de la consulta sin optimizar con el optimizado. Tenga en
cuenta que puede crear índices, siempre y cuando se tenga en cuenta las consideraciones de este
documento

1. Mostrar por departamento el nombre del jefe, cantidad de empleados y el maximo salario
del pais en la cual esta ubicado.
2. Listar los empleados que tengan un salario mayor al promedio de salarios del
departamento de SALES
3. Listar el departamento con mas empleados
4. Mostrar los compañeros de oficina (que tengan el mismo jefe)de Neena
5. Listar los departamentos en los cuales hayan al menos la misma cantidad de empleados de
que el departamento Marketing y que su jefe tenga un salario mayor al promedio de los
salarios de todos los jefes.

También podría gustarte