Pregunta

Tengo curiosidad por cuál de las siguientes a continuación sería más eficiente?

Siempre he sido un poco cauteloso sobre el uso IN porque creo SQL Server activa el conjunto de resultados en una declaración de gran IF. Para un gran conjunto de resultados, esto podría resultar en un rendimiento inferior. Para los pequeños conjuntos de resultados, yo tampoco estoy seguro es preferible. Para grandes conjuntos de resultados, no EXISTS ser más eficiente?

WHERE EXISTS (SELECT * FROM Base WHERE bx.BoxID = Base.BoxID AND [Rank] = 2)

vs.

WHERE bx.BoxID IN (SELECT BoxID FROM Base WHERE [Rank = 2])
¿Fue útil?

Solución

EXISTS será más rápido porque una vez que el motor ha encontrado un éxito, será dejar de mirar como la condición ha resultado cierto.

Con IN, será recoger todos los resultados de la sub-consulta antes de procesamiento adicional.

Otros consejos

La respuesta aceptada es miope y la cuestión un poco flojo en la que:

  

1) Ni menciona explícitamente si un índice de cobertura está presente en   la izquierda, derecha, o en ambos lados.

     

2) Ni tiene en cuenta el tamaño de la entrada izquierda conjunto lado y   entrada de ajuste del lado derecho.
        (La pregunta simplemente menciona un gran resultado global Set).

Creo que el optimizador es lo suficientemente inteligente como para convertir entre "en" vs "existe" cuando hay una diferencia de costo significativo debido a (1) y (2), de lo contrario, sólo puede ser utilizado como una indirecta (por ejemplo, existe para fomentar el uso de un índice reubicable en el lado derecho).

Las dos formas se pueden convertir a unirse a las formas internamente, han invertido el orden de combinación, y se ejecutan como lazo, de hash o se fusionan - basándose en los recuentos estimados de línea (izquierda y derecha) y la existencia de índice en la izquierda, derecha, o ambas lados.

He hecho algunas pruebas en SQL Server 2005 y 2008, y tanto en el existe y el EN regreso con el mismo plan de ejecución real exacto, como otros han dicho. El optimizador es óptima. :)

Algo a tener en cuenta, sin embargo, existe, EN, y unirse a veces puede devolver resultados diferentes si no lo hace plantear la consulta a la perfección: http://weblogs.sqlteam.com/mladenp/archive/2007/05/18/60210.aspx

Me gustaría ir con EXISTE EN encima, ver enlace abajo:

de SQL Server: REGISTRARSE EN vs vs EXISTE - la lógica diferencia

Los planes de ejecución están normalmente van a ser idénticos en estos casos, pero hasta que vea cómo los factores del optimizador en todos los demás aspectos de índices, etc., que realmente nunca sabrán.

Así que, en no es lo mismo como existe ni se producirá el mismo plan de ejecución.

Por lo general, existe se utiliza en una consulta correlacionada, eso significa que se unirá a la EXISTE consulta interna con su consulta externa. Que añadirá más pasos para producir un resultado como sea necesario para resolver la consulta externa se une a la consulta interna y se une a continuación coinciden con sus cláusulas, donde se unen a ambos.

lo general en se utiliza sin correlacionar la consulta interna con la consulta externa, y que puede ser resuelto en un solo paso (en el mejor de los casos).

Considere esto:

  1. Si utiliza IN y el resultado de la consulta interna es millones de filas de valores distintos, es probable que realizar más lento que EXISTS dado que la EXISTE consulta es performant (tiene los índices adecuados para unirse con la consulta externa).

  2. Si utiliza existe y la unión con su consulta externa es compleja (toma más tiempo para llevar a cabo, sin índices adecuados) se ralentizará la consulta por el número de filas en la tabla externa, a veces el tiempo estimado para completa puede ser en días. Si el número de filas es aceptable para su hardware dado, o la cardinalidad de los datos es correcta (por ejemplo, menos valores distintos en un gran conjunto de datos) EN pueden realizar más rápido que existe.

  3. Todo lo anterior se observará cuando se tiene una buena cantidad de filas en cada tabla (por justo me refiero a algo que supera el procesamiento de la CPU y / o umbrales de RAM para el almacenamiento en caché).

Así que la respuesta es que depende. Se puede escribir una consulta compleja en el interior IN o existe, pero como regla general, usted debe tratar de usar IN con un conjunto limitado de valores distintos y que existe cuando se tiene una gran cantidad de filas con una gran cantidad de valores distintos.

El truco es limitar el número de filas que se escaneados.

Saludos,

MarianoC

Para optimizar la EXISTS, ser muy literales; algo sólo tiene que estar ahí, pero que en realidad no necesita ningún datos devueltos por la subconsulta correlacionada. No eres más que la evaluación de una condición booleana.

Así que:

WHERE EXISTS (SELECT TOP 1 1 FROM Base WHERE bx.BoxID = Base.BoxID AND [Rank] = 2)

Debido a que el sub-consulta correlacionada es RBAR, el exitoso primer resultado hace que la condición de verdad, y se procesa sin más.

Hay muchas respuestas engañosas respuestas aquí, incluyendo el altamente upvoted (aunque no creo que sus operaciones destinadas daño). La respuesta corta es: Estos son los mismos

.

Hay muchas palabras clave en el (T) lenguaje SQL, pero al final, la única cosa que realmente sucede en el hardware es las operaciones como se ve en el plan de consulta ejecución.

La operación de relación (teoría matemática) que hacemos cuando invocamos [NOT] IN y [NOT] EXISTS es la semi unen (anti-unirse al utilizar NOT). No es una coincidencia que las operaciones correspondientes en SQL Server tienen el mismo nombre . No hay ninguna operación que menciona IN o EXISTS en cualquier lugar - solamente (anti) semi une. Por lo tanto, no hay manera de que un IN lógicamente equivalente vs elección EXISTS podría afectar el rendimiento porque hay una y única manera, el (anti) semi unirse a la operación de ejecución, para obtener sus resultados .

Un ejemplo:

Consulta 1 ( plan)

select * from dt where dt.customer in (select c.code from customer c where c.active=0)

Consulta 2 ( plan)

select * from dt where exists (select 1 from customer c where c.code=dt.customer and c.active=0)

De la parte superior de mi cabeza y no garantiza que sea correcta: Creo que el segundo será más rápida en este caso.

  1. En la primera, la subconsulta correlacionada probablemente hará que la subconsulta para ser ejecutado para cada fila.
  2. En el segundo ejemplo, la subconsulta debe ejecutar solamente una vez, ya que no correlacionados.
  3. En el segundo ejemplo, el IN un cortocircuito en tan pronto como se encuentra una coincidencia.
Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top