2009-06-09 15 views
9

Como DBA para MS SQL 2000 y 2005, veo regularmente consultas de selección gigantes UNIENDO 7-10 o incluso más tablas. Sin embargo, encuentro que hay un cierto punto pasado que el rendimiento tiende a sufrir y la consulta se vuelve muy difícil de depurar y/o mejorar.¿Cuántas tablas son "demasiadas" en un único SQL SELECT?

Entonces, ¿hay una "regla de oro" para cuando debería considerar otros métodos de consulta, como tablas temporales para mantener los resultados preliminares? ¿O hay un punto después del cual el optimizador de consultas SQL simplemente no hace un buen trabajo al determinar el mejor plan?

+0

Pregunta similar: http://stackoverflow.com/questions/793647/is-too-many-left-joins-a-code-smell –

Respuesta

7

Muchas veces puedes aliviar el olor visual creando vistas de ayuda, no creo que haya una regla difícil de cuantas combinaciones se consideran malas.

A diferencia de la codificación de procedimientos, dividir SQL en pequeños fragmentos puede dar lugar a consultas ineficaces.

SQL Optimiser funcionará muy bien con toneladas de combinaciones de tablas, y si tocas una esquina, puedes especificar el orden de unión o el estilo con sugerencias. En realidad, creo que es muy raro obtener consultas que se unan a más de 10 tablas, pero es bastante factible que esto ocurra en un escenario de tipo de informe.

Si descubre una situación en la que tiene muchas uniones Y ha descubierto que esta consulta en particular es un cuello de botella Y tiene todos los índices correctos en su lugar, probablemente necesite refactorizar. Sin embargo, tenga en cuenta que la gran cantidad de uniones puede ser solo un síntoma, no la causa raíz del problema. Se debe seguir la práctica estándar para la optimización de consultas (ver perfil, plan de consulta, estructura de base de datos, lógica, etc.)

SQL Server usa tempdb de todos modos para unir uniones, por lo que generalmente no es necesario crear tablas temporales solo para refactorizar una sola consulta SELECT.

+0

Me alejo de las vistas de ayudante, porque con frecuencia pueden contener columnas adicionales, filtros , lógica o combinaciones que parecen hacer que la vista sea "agradable" de usar en un sentido general, pero puede no ser necesaria para una consulta específica. Acabo de refactorizar una consulta compleja que estaba utilizando una vista particularmente mala con un filtro inútil en una columna no indexada. ("DONDE INACTIVO = 0" pero ninguna de las 16 millones de filas realmente tenía este indicador) – BradC

+0

Cierto, al igual que cualquier refactorización, esta técnica puede ser mal utilizada. Creo que debería considerar las vistas de ayuda si va a ayudar a varias consultas (no solo para refactorizar una sola consulta) –

1

Depende de lo grande que sean sus tablas, incluso si solo junta 2 tablas si tiene 100M de registros, entonces ese será un proceso lento de todos modos.

Si tiene registros X en los registros de la tabla ay Y en la tabla b, si los une, puede obtener hasta x * y registros de nuevo, en ese caso la memoria de intercambio se utilizará durante el proceso , eso va a ser lento, compara eso, las pequeñas consultas solo usan la caché CPU L2 que tiene el mejor rendimiento.

Sin embargo, si realmente necesita juntar muchas tablas para lograr el objetivo, sugiero que sus bases de datos estén sobre normalizadas, la 3ra normalización funciona muy bien en la mayoría de los escenarios, no intente escupir la información demasiado, ya que reconoce ser ineficiente para consultar.

Sí, si es necesario, cree una tabla para almacenar en caché los resultados de la consulta pesada y actualice los campos solo cuando sea necesario o incluso solo una vez al día.

0

También veo consultas enormes unir 7-10 tablas, pero por lo que he visto, el optimizador de consultas siempre parece encontrar el plan más eficiente; sin duda, todos los problemas de rendimiento que veo en este tipo de problemas complejos suelen estar relacionados a algún otro problema (como sentencias WHERE condicional o subconsultas anidadas)

0

El optimizador establece un límite de tiempo sobre sí mismo para evitar que se ejecute demasiado tiempo. El problema con muchas tablas es que cada una multiplica el número de planes posibles para que el optimizador los evalúe (en realidad es el número de combinaciones, no tablas per se). En algún momento, el optimizador se queda sin tiempo y solo usará el mejor plan que tiene hasta ahora, lo que puede ser bastante malo.

Entonces, ¿dónde está este punto? Bueno, es muy situacional, y 2005 es mucho mejor que 2000, pero mi regla general es 4-8 para SQL Server 2000 y 6-16 para SQL Server 2005.

0

Hay otras variables involucradas que tienen una mayor impacto significativo en el plan de consulta general y el rendimiento, en mi experiencia, tales como:

  • la entrada recuentos de filas para cada operador de combinación
  • la eficiencia con los datos de entrada se pueden recuperar en el primer lugar
  • la tamaño y tipo de las columnas que se unen (p. ej., conversiones de tipo, nulabilidad)

Es posible que solo tenga dos tablas unidas en una consulta, pero si una columna clave es un GUID y la otra es una representación varchar de un GUID, no tiene índices en ninguna parte, y las tablas son 2 millones de filas cada uno, entonces probablemente obtendrá un rendimiento muy pobre.

He codificado las consultas de informes con más de 10 combinaciones antes, y el uso juicioso de algunos índices no agrupados en columnas de clave externa suele tener el mayor beneficio en el plan.

+0

El optimizador de SQL Server no verá todas sus combinaciones si tiene mucho, por lo que si conoce ciertas combinaciones ayudará más que otros en su consulta, hay una ventaja para moverlos hacia arriba en la lista. – Joe

Cuestiones relacionadas