¿Agregar DISTINCT
en el siguiente ejemplo tiene algún impacto en el tiempo de ejecución de la consulta?
¿Es aconsejable usarlo como una pista a veces?
SELECT *
FROM A
WHERE A.SomeColumn IN (SELECT DISTINCT B.SomeColumn FROM B)
¿Agregar DISTINCT
en el siguiente ejemplo tiene algún impacto en el tiempo de ejecución de la consulta?
¿Es aconsejable usarlo como una pista a veces?
SELECT *
FROM A
WHERE A.SomeColumn IN (SELECT DISTINCT B.SomeColumn FROM B)
Respuestas:
Al preguntarse sobre cosas como esta, debe comparar los planes de ejecución de sus consultas.
La forma del plan de ejecución para su consulta, por supuesto, diferirá dependiendo de cuántas filas tenga en sus tablas y qué índices estén definidos.
Un escenario que muestra que no hay diferencia en el rendimiento es cuando hay sustancialmente más filas de las A
que hay B
. Luego, el optimizador elegirá B
como la tabla de conducción en una unión de bucle anidado A
. Para obtener un resultado correcto, debe usar un Agregado de flujo en la tabla B
en ambas consultas para obtener solo las filas distintas B
. Entonces, en este caso, la palabra clave distinta no tiene impacto en el rendimiento.
El plan de ejecución para probar otros dos casos obvios, más filas en B que A e igual número de filas en las tablas, también muestra exactamente el mismo plan de ejecución para las consultas.
Actualizar
Antes de que tenga lugar la optimización de la consulta, la consulta pasa por una fase de simplificación. Puede ver cómo se ve el árbol lógico utilizando la marca de seguimiento 8606.
El árbol de entrada para las consultas son claramente diferentes, pero después de la simplificación son los mismos.
Ref: Más indicadores de seguimiento del optimizador de consultas no documentados y inmersión profunda del optimizador de consultas - Parte 2
Árbol de entrada y árbol simplificado para la consulta utilizando distintos:
*** Input Tree: ***
LogOp_Project QCOL: [xx].[dbo].[A].SomeColumn
LogOp_Select
LogOp_Get TBL: A A TableID=213679909 TableReferenceID=0 IsRow: COL: IsBaseRow1002
ScaOp_SomeComp 2
ScaOp_Identifier QCOL: [xx].[dbo].[A].SomeColumn
LogOp_GbAgg OUT(QCOL: [xx].[dbo].[B].SomeColumn,) BY(QCOL: [xx].[dbo].[B].SomeColumn,)
LogOp_Project
LogOp_Project
LogOp_Get TBL: B B TableID=229679966 TableReferenceID=0 IsRow: COL: IsBaseRow1006
AncOp_PrjList
AncOp_PrjList
AncOp_PrjList
AncOp_PrjList
*******************
*** Simplified Tree: ***
LogOp_LeftSemiJoin
LogOp_Get TBL: A A TableID=213679909 TableReferenceID=0 IsRow: COL: IsBaseRow1002
LogOp_Get TBL: B B TableID=229679966 TableReferenceID=0 IsRow: COL: IsBaseRow1006
ScaOp_Comp x_cmpEq
ScaOp_Identifier QCOL: [xx].[dbo].[A].SomeColumn
ScaOp_Identifier QCOL: [xx].[dbo].[B].SomeColumn
*******************
Árbol de entrada y árbol simplificado para consultas que no usan distintivo
*** Input Tree: ***
LogOp_Project QCOL: [xx].[dbo].[A].SomeColumn
LogOp_Select
LogOp_Get TBL: A A TableID=213679909 TableReferenceID=0 IsRow: COL: IsBaseRow1002
ScaOp_SomeComp 2
ScaOp_Identifier QCOL: [xx].[dbo].[A].SomeColumn
LogOp_Project
LogOp_Get TBL: B B TableID=229679966 TableReferenceID=0 IsRow: COL: IsBaseRow1006
AncOp_PrjList
AncOp_PrjList
*******************
*** Simplified Tree: ***
LogOp_LeftSemiJoin
LogOp_Get TBL: A A TableID=213679909 TableReferenceID=0 IsRow: COL: IsBaseRow1002
LogOp_Get TBL: B B TableID=229679966 TableReferenceID=0 IsRow: COL: IsBaseRow1006
ScaOp_Comp x_cmpEq
ScaOp_Identifier QCOL: [xx].[dbo].[A].SomeColumn
ScaOp_Identifier QCOL: [xx].[dbo].[B].SomeColumn
*******************