2009-05-18 11 views
9

Si funciono con la siguiente consulta SQLSQL de las operaciones

SELECT * 
FROM A 
LEFT JOIN B 
ON A.foo=B.foo 
WHERE A.date = "Yesterday" 

¿El documento WHERE se evalúan antes o después de la JOIN?

Si después, ¿cuál sería una mejor manera de escribir esta declaración para que solo se devuelvan las filas en A de "Yesterday" se unen a B?

+0

'lo que sería una mejor manera de escribir esta declaración de manera que sólo las filas de una de "Ayer" se unen a B.' (respuesta tardía) -> 'INNER JOIN' –

Respuesta

8

Depende de la base de datos.

En SQL Server, ejecute: SET SHOWPLAN_ALL ON luego ejecute la consulta, obtendrá una idea de lo que sucede cuando se ejecuta.

1

Depende de los índices y las estadísticas.

Debe mostrar la ruta de ejecución de la consulta para determinar dónde se deben aplicar las optimizaciones (si las hay).

5

Semánticamente: después de JOIN. Pero en este caso, no hay diferencia en el tiempo, porque está en el lado IZQUIERDO de JOIN.

Como ya lo tiene, "solo las filas en A desde" Ayer "se unen a B".

El optimizador es libre de reorganizar su orden de operaciones en función de las equivalencias en el álgebra relacional.

Esto devuelve sólo A.date = "Ayer" y se une a B, donde se puede encontrar una coincidencia en foo:

SELECT * FROM A 
LEFT JOIN B 
    ON A.foo=B.foo 
WHERE A.date="Yesterday" 

Esto devuelve todos los A, independientemente de cualquier criterio y se une a B donde A.date =" Ayer "Y encuentra una coincidencia en foo:

SELECT * FROM A 
LEFT JOIN B 
    ON A.foo=B.foo 
    AND A.date="Yesterday" 
+0

Para entender, ¿estás diciendo que poner los criterios en la cláusula WHERE es mejor desde una perspectiva de rendimiento que ponerlo dentro de la cláusula JOIN? – NotMe

+0

No hace ninguna diferencia al rendimiento en una UNIÓN INTERNA y es por eso que el optimizador tiene más opciones para mover cosas en UNIONES INTERIORES. En una UNIÓN EXTERIOR (IZQUIERDA o DERECHA), afecta la semántica de la declaración, por lo que el rendimiento no suele ser el problema. –

7

Su idea de" evaluación "no es correcta ya que SQL es un lenguaje declarativo.

Por cierto, puede ver el plan de ejecución de la consulta. En MySQL, prefija su consulta con la palabra clave describe para ver el plan de ejecución.

2

El orden de las operaciones para satisfacer una consulta se determina por qué el capricho del optimizador de consultas de la base de datos particular. Un optimizador de consultas intenta producir un buen "plan de consulta" (conjunto de operaciones) basado en lo que puede obtener de la consulta y cualquier estadística que tenga sobre la base de datos (que podría incluir la cardinalidad de las tablas y ciertas distribuciones de datos) .

En su caso, la respuesta puede depender de si usted tiene un índice secundario en A.date

optimización de la consulta de un tema bastante rica. La documentación de cualquier base de datos que esté utilizando tendrá mucho más que decir al respecto.

1

en SQL Server:

Como regla general, cláusulas JOIN se evalúan antes de las cláusulas WHERE.

En caso de complejo se une a que los filtros de necesidad en la parte unirse, las escribo junto con mi unen

SELECT * 
FROM A 
LEFT JOIN B 
    ON A.Foo1 = B.Foo1 
    And A.Date = 'Yesterday' 
OUTER JOIN C 
    ON B.Foo2 = C.Foo2 
JOIN D 
    ON B.Foo3 = D.Foo3 
+0

Esto no tiene el mismo significado cuando lo usa dentro de IZQUIERDA. En LEFT JOIN, cuando no se satisfacen los criterios, las filas IZQUIERDAS aún se devuelven, y las columnas de DERECHO son NULAS. –

+0

Me corrigen en el ejemplo proporcionado. Estaba tratando de poner el punto donde una parte de una cláusula junto con la unión apropiada. He corregido la declaración. –

+0

:) me paro recorrected .. no puedo corregir la declaración. –

0
SELECT * 
FROM (SELECT * FROM A WHERE Date = 'Yesterday') A 
LEFT JOIN B 
    ON A.Foo1 = B.Foo1 
OUTER JOIN C 
    ON B.Foo2 = C.Foo2 
JOIN D 
    ON B.Foo3 = D.Foo3 
Cuestiones relacionadas