Trabajo en el equipo de SQL Server y espero aclarar algunos puntos en este hilo (no lo había visto anteriormente, así que lamento que el equipo de ingeniería no lo haya hecho antes).
En primer lugar, no existe una diferencia semántica entre select count(1) from table
vs select count(*) from table
. Devuelven los mismos resultados en todos los casos (y es un error si no). Como se señaló en las otras respuestas, select count(column) from table
es semánticamente diferente y no siempre devuelve los mismos resultados que count(*)
.
En segundo lugar, con respecto al rendimiento, hay dos aspectos que serían importantes en SQL Server (y SQL Azure): trabajo en tiempo de compilación y trabajo en tiempo de ejecución. El trabajo del tiempo de compilación es una cantidad trivialmente pequeña de trabajo adicional en la implementación actual. Hay una expansión de * a todas las columnas en algunos casos, seguida de una reducción a 1 columna que se genera debido a cómo algunas de las operaciones internas funcionan en el enlace y la optimización. Dudo que aparezca en cualquier prueba medible, y es probable que se pierda en el ruido de todas las otras cosas que suceden debajo de las cubiertas (como estadísticas automáticas, sesiones xevent, gastos generales de almacenamiento de consultas, disparadores, etc.). Es tal vez unos pocos miles de instrucciones de CPU adicionales. Entonces, count (1) hace un poco menos de trabajo durante la compilación (lo que generalmente sucederá una vez y el plan se almacena en caché en varias ejecuciones posteriores). Para el tiempo de ejecución, suponiendo que los planes sean los mismos, no debería haber una diferencia medible. (Uno de los ejemplos anteriores muestra una diferencia: lo más probable es que se deba a otros factores en la máquina si el plan es el mismo).
En cuanto a cómo el plan puede ser potencialmente diferente. Es muy poco probable que sucedan, pero es potencialmente posible en la arquitectura del optimizador actual. El optimizador de SQL Server funciona como un programa de búsqueda (piense: un programa de computadora que juega al ajedrez buscando a través de varias alternativas para diferentes partes de la consulta y calcula las alternativas para encontrar el plan más barato en un tiempo razonable). Esta búsqueda tiene algunos límites sobre cómo funciona para mantener la compilación de consultas terminando en un tiempo razonable. Para consultas más allá de lo más trivial, hay fases de la búsqueda y se ocupan de tramos de consultas en función de lo costoso que el optimizador cree que la consulta es potencialmente ejecutable. Hay 3 fases de búsqueda principales, y cada fase puede ejecutar heurísticas más agresivas (costosas) tratando de encontrar un plan más barato que cualquier solución anterior. En última instancia, hay un proceso de decisión al final de cada fase que intenta determinar si debe devolver el plan que encontró hasta ahora o si debe seguir buscando. Este proceso utiliza el tiempo total empleado hasta ahora frente al costo estimado del mejor plan encontrado hasta el momento. Por lo tanto, en diferentes máquinas con diferentes velocidades de CPU es posible (aunque raro) obtener diferentes planes debido al tiempo de espera en una fase anterior con un plan en lugar de continuar en la siguiente fase de búsqueda. También hay algunos escenarios similares relacionados con el tiempo de espera de la última fase y la posibilidad de quedarse sin memoria en consultas muy costosas que consumen toda la memoria en la máquina (no suele ser un problema en 64 bits, pero fue una preocupación mayor) de nuevo en servidores de 32 bits). En última instancia, si obtiene un plan diferente, el rendimiento en tiempo de ejecución sería diferente. Yo no'
Net-net: utilice cualquiera de los dos que desee, ya que nada de esto importa de forma práctica. (Hay factores mucho, mucho más grandes que afectan el rendimiento en SQL más allá de este tema, sinceramente).
Espero que esto ayude. Escribí un capítulo del libro sobre cómo funciona el optimizador, pero no sé si es apropiado publicarlo aquí (ya que creo que recibo pequeñas regalías). Entonces, en lugar de publicar eso, publicaré un enlace a una charla que di en SQLBits en el Reino Unido sobre cómo funciona el optimizador a un alto nivel para que pueda ver las diferentes fases principales de la búsqueda con un poco más de detalle si lo desea para aprender sobre eso. Aquí está el enlace del video: https://sqlbits.com/Sessions/Event6/inside_the_sql_server_query_optimizer