SQL Server Join / donde se procesa el orden

18

Después de leer la consulta SQL lenta, no estoy seguro de cómo optimizar , me hizo pensar en el rendimiento general de las consultas. Seguramente, necesitamos que los resultados de la primera tabla (cuando se unen otras tablas) sean lo más pequeños posible antes de unirse (uniones internas para esta pregunta) para que nuestras consultas sean un poco más rápidas.

Ejemplo, si esto:

SELECT *
FROM   ( SELECT * FROM table1 WHERE col = @val ) t
INNER JOIN table2 ON col = col2

Sé mejor / más rápido que:

SELECT *
FROM table1
INNER JOIN table2 ON col = col2
WHERE table1.col = @val

Mi teoría es la siguiente (esta podría no ser la implementación correcta, estoy tratando de recordar de un libro interno de SQL Server 2008 que leí (MSFT Press)):

  1. El procesador de consultas primero obtiene la tabla izquierda (tabla1)
  2. Se une a la segunda tabla (tabla2) y forma un producto cartesiano antes de filtrar las filas necesarias (si corresponde)
  3. Luego realiza las cláusulas WHERE, ORDER BY, GROUP BY, HAVING con la instrucción SEELCT en último lugar.

Entonces, si en la declaración n. ° 1 anterior, la tabla es más pequeña, el motor SQL tiene menos trabajo que hacer al formar los productos cartesianos. Luego, cuando alcanza la instrucción where, tiene un conjunto de resultados reducido desde el cual filtrar en la memoria.

Podría estar tan lejos de la marca que es irreal. Como dije, es una teoría.

¿Tus pensamientos?

Nota : Acabo de pensar en esta pregunta y aún no he tenido la oportunidad de realizar ninguna prueba.

Nota 2 : Etiquetado como SQL Server ya que no sé nada sobre la implementación de MySql, etc. No dude en responder / comentar de todos modos

Stuart Blackler
fuente

Respuestas:

15

El procesamiento lógico de una consulta está en MSDN (escrito por el equipo de Microsoft SQL Server, no por terceros)

1. FROM
2. ON
3. JOIN
4. WHERE
5. GROUP BY
6. WITH CUBE or WITH ROLLUP
7. HAVING
8. SELECT
9. DISTINCT
10. ORDER BY
11. TOP

Una tabla derivada sigue esto, luego la consulta externa lo vuelve a hacer, etc.

Sin embargo, esto es lógico : no real . No importa cómo lo haga realmente SQL Server, estas semánticas son respetadas al pie de la letra . El "real" está determinado por el Optimizador de consultas (QO) y evita el producto de Cartesión intermedio que mencionó.

Vale la pena mencionar que SQL es declarativo: usted dice "qué" no "cómo" como lo haría para una programación procesal / imperativa (Java, .net). Por lo tanto, decir "esto sucede antes de eso" es incorrecto en muchos casos (por ejemplo, suposición de cortocircuitos u orden L-to-R WHERE)

En su caso anterior, el QO generará el mismo plan sin importar cómo esté estructurado porque es una consulta simple.

Sin embargo, el QO se basa en los costos y para una consulta compleja puede llevar 2 semanas generar el plan ideal. Por lo tanto, hace "lo suficientemente bueno" que en realidad no lo es.

Por lo tanto, su primer caso puede ayudar al optimizador a encontrar un mejor plan porque el orden de procesamiento lógico es diferente para las 2 consultas. Pero puede que no.

He usado este truco en SQL Server 2000 para obtener una mejora de rendimiento de velocidad 60 veces mayor en las consultas de informes. A medida que el QO mejora de una versión a otra, mejora su resolución.

Y el libro que mencionó: hay una disputa al respecto.
Consulte SO y los enlaces siguientes: /programming//q/3270338/27535

gbn
fuente
6

Una consulta SQL no es de naturaleza procesal, no hay procesamiento de arriba a abajo de los operadores de unión. El orden de las tablas en sus consultas de ejemplo no influye en el plan de ejecución, ya que son lógicamente equivalentes y generarán exactamente el mismo plan.

Ha evaluado dos de las opciones que el optimizador de consultas podría considerar al generar un plan para esta consulta. El factor principal que influye en la elección del plan son las estadísticas de las tablas involucradas y los costos asociados con las elecciones del operador en cualquier plan candidato.

Una combinación de dos tablas muy simple, como su ejemplo, podría satisfacerse con cualquiera de los cientos de planes de ejecución diferentes. El optimizador decide cuál será la mejor manera de responder a su consulta comparando los costos de estos planes.

A veces se equivoca y puede ayudarlo a tomar mejores decisiones a través de una indexación mejorada, manteniendo estadísticas actualizadas y aplicando sugerencias. En casos muy raros, es posible que desee forzar el orden de ejecución utilizando la sugerencia FORCE ORDER, pero eso debe usarse con moderación. Es un martillo para romper una tuerca, el optimizador generalmente puede burlarse para generar mejores planes al proporcionarle mejor información.

Mark Storey-Smith
fuente