Optimización de rendimiento en MySQL

mysqlEn ocasiones intentamos que nuestras aplicaciones sean lo más eficientes posibles, que sean muy cuidadosas en la cantidad de memoria que utilizan, que hagan el mínimo número de consultas a base de datos y que solo accedan a ellas cuando es realmente necesario. Todo esto no puede dejarse de lado pero de poco servirá si nuestra base de datos no está bien diseñada o si no conocemos como afecta al rendimiento diseñar una tabla o una consulta de diferentes formas.

Cuando te encuentras ante tablas muy grandes y con muchos accesos concurrentes, empiezas a preguntarte si el diseño es optimo o si podrías llegar a reducir el tiempo de acceso a ellas. En este post intentaré explicar algunas soluciones para mejorar el trabajo con bases de datos y hacer un mejor diseño y nuestras consultas algo más rápidas.

Particionado de tablas

El particionado es uno de los puntos más críticos en tablas con muchas entradas y es capaz de acelerar mucho nuestras consultas. En este punto tenemos dos tipos de particionado, particionado vertical y particionado horizontal el cual no será explicado en este post y que posiblemente será explicado en un futuro (aquí tienes un enlace con ejemplos de implementación). Por otro lado, el particionado vertical consiste en dividir la tabla en otras tablas más pequeñas según el tipo de información que esta contenga. Esto permite tener tablas con un número menor de campos y permite acelerar las búsquedas. Por ejemplo, si tenemos una tabla de usuarios con los siguientes campos:

id, nombre, apellidos, pin, contrasena, cuentaBloqueada, ultimoAcceso

nos daremos cuenta de que, muy posiblemente, no accedamos las mismas veces a un tipo de dato o a otro y que podemos hacer una división lógica entre ellos. De esta forma, podríamos dividir esta tabla en tres tablas más pequeñas:

id, ultimoAcceso
id, nombre, apellidos
id, pin, contrasena, cuentaBloqueada

Eso dependerá siempre del diseño de nuestra aplicación y no debe tomarse al pie de la letra, no tendría mucho sentido tener esta división si en cada acceso de usuario a nuestro sistema o por cada acción que éste realiza tengo que trabajar con las tres tablas y empezar a usar inner joins para obtener la información necesaria.

Claves primarias

Las búsquedas en nuestras tablas serán mucho más rápidas si nuestras claves primarias son numéricas, autoincrementales y sin signo (unsigned). Aunque esto no es lo que suelen enseñarnos en clase, a veces es mejor crear autoindices como claves primarias antes que aprovechar posibles campos únicos existentes como, por ejemplo, un DNI o una matrícula.

No tener campos nulos

No hay ninguna diferencia funcional entre permitir campos nulos o asignar un “0” a un campo numérico o dejar en blanco un campo String. Trabajar con campos nulos consume recursos así que evitando usar campos nulos puede llegar a mejorar la eficiencia de nuestras consultas en tablas grandes.Acostúmbrate a usar campos NOT NULL.

Índices

Es importante seleccionar bien los índices que incluimos en nuestras tablas. Los índices ocupan memoria pero nos permiten acelerar las búsquedas, por lo tanto, puede ser una buena idea utilizar índices en aquellos campos que utilizamos para realizar filtros a nuestras consultas, por ejemplo, en los utilizados en las cláusulas WHERE o en los INNER JOIN. Tampoco es una buena practica llenar las tablas de índices así que úsalos con moderación.

Uso de la cache

Es recomendable no utilizar las funciones sysdate() o now() en las clausulas WHERE. Estas funciones obligan a relizar una búsqueda en nuestras tablas en lugar de utlizar la caché de consultas anteriores. És mejor obtener la fecha con anterioridad y posteriormente utilizarla en nuestras consultas que hacerlo directamente en ellas. (Más sobre el uso de la caché)

Timestamp en lugar de datetime

Podemos acelerar las búsuqedas en nuestra base de datos si modificamos nuestros detetime por timestamp. Además, el tipo datetime ocupa 8 bytes en lugar de los 4 que ocupa el timestamp.

Mejor char que varchar

Si conocemos el tamaño exacto que va a tener un campo de texto (por ejemplo, un DNI o ID) es mejor optar por el uso de CHAR en lugar de VARCHAR.

Evitar el uso de SELECT *

Debemos seleccionar la información que realmente necesitamos. Si únicamente necesito obtener nombre y apellidos de un usuario concreto no tiene sentido pedirle a nuestro SGBD que nos devuelva toda la información de un usuario concreto. És bueno acostumbrarnos a pedir exactamente la información que vamos a necesitar.

Anuncios

Responder

Introduce tus datos o haz clic en un icono para iniciar sesión:

Logo de WordPress.com

Estás comentando usando tu cuenta de WordPress.com. Cerrar sesión / Cambiar )

Imagen de Twitter

Estás comentando usando tu cuenta de Twitter. Cerrar sesión / Cambiar )

Foto de Facebook

Estás comentando usando tu cuenta de Facebook. Cerrar sesión / Cambiar )

Google+ photo

Estás comentando usando tu cuenta de Google+. Cerrar sesión / Cambiar )

Conectando a %s

A %d blogueros les gusta esto: