HAVING frente a WHERE
Compare el filtrado antes y después de agrupar y determine qué cláusula puede ver la agregación
HAVING frente a WHERE es una lección gratuita de SQL Interview Prep en CoddyKit. Esta es la lección 2 de 4. Puedes leer la lección completa abajo gratuitamente — luego la practicas en el navegador con un editor de código integrado y un tutor de IA 24/7. Forma parte de la ruta de aprendizaje de SQL Interview Prep, y tu progreso se sincroniza en la web y la app de CoddyKit. El curso de SQL Interview Prep incluye 4 lecciones en total.
La pregunta que le harán
«¿Cuál es la diferencia entre WHERE y HAVING?» es una de las preguntas más frecuentes en las entrevistas de SQL. Una respuesta débil dice: «HAVING se usa para las funciones de agregación». Una respuesta sólida explica cuándo se ejecuta cada cláusula en la secuencia de procesamiento de la consulta.
Ese momento es lo esencial: WHERE filtra las filas antes de la agrupación; HAVING filtra los grupos después de la agregación.
Dónde se sitúan en el orden de ejecución
Recuerde el orden lógico de ejecución de una consulta:
FROM/JOIN→ construir el conjunto de filasWHERE→ filtrar filas individualesGROUP BY→ agrupar las filasHAVING→ filtrar los gruposSELECT→ proyectar las columnasORDER BY→ ordenar
WHERE se ejecuta antes de que existan los grupos; HAVING se ejecuta después, por lo que HAVING puede ver las funciones de agregación y WHERE no.
WHERE no puede ver las funciones de agregación
Como WHERE se ejecuta antes de la agrupación, todavía no existen valores agregados. Escribir WHERE COUNT(*) > 5 provoca un error de sintaxis en cualquier base de datos estándar.
Los entrevistadores incluyen exactamente esta línea para comprobar si entiende la secuencia de procesamiento. La función de agregación no existe cuando se evalúa WHERE.
-- ERROR: aggregate not allowed in WHERE
SELECT department, COUNT(*)
FROM employees
WHERE COUNT(*) > 5
GROUP BY department;HAVING filtra los grupos
Mueva la condición de agregación a HAVING y funcionará, porque HAVING se ejecuta después de que se calculan los grupos y sus agregados.
Interprételo así: «agrupe los empleados y, después, conserve únicamente los departamentos cuyo recuento sea superior a cinco».
SELECT department, COUNT(*) AS headcount
FROM employees
GROUP BY department
HAVING COUNT(*) > 5;Coloque los filtros de filas en WHERE
El error inverso consiste en filtrar las filas sin agregar en HAVING. A menudo produce la respuesta correcta, pero es más lento y engañoso, porque agrupó filas que pretendía descartar.
Regla práctica: filtre por un valor de columna sin agregar → WHERE. Filtre por un agregado → HAVING. Filtrar las filas al principio reduce los datos que debe procesar la agrupación.
-- Better: drop inactive rows BEFORE grouping
SELECT department, COUNT(*) AS headcount
FROM employees
WHERE status = 'active'
GROUP BY department
HAVING COUNT(*) > 5;Ambas cláusulas juntas
Una consulta completa suele utilizar ambas cláusulas. WHERE reduce primero las filas; después, HAVING conserva los grupos que cumplen los requisitos. Leerla de arriba abajo coincide con el orden lógico.
Ejemplo resuelto: entre los pedidos realizados este año, encuentre los clientes cuyo gasto total supere 1000.
SELECT customer_id, SUM(amount) AS total_spent
FROM orders
WHERE order_date >= '2024-01-01'
GROUP BY customer_id
HAVING SUM(amount) > 1000;HAVING con columnas no agregadas
HAVING puede hacer referencia a una columna de agrupación, no solo a agregados. HAVING department = 'Sales' es legal, pero no tiene sentido: ese filtro debe estar en WHERE para ejecutarse antes.
Si un entrevistador le muestra un HAVING que filtra una columna agrupada simple, la crítica esperada es: «muévalo a WHERE para mejorar la eficiencia».
-- Works but inefficient; prefer WHERE department = 'Sales'
SELECT department, COUNT(*)
FROM employees
GROUP BY department
HAVING department = 'Sales';HAVING sin GROUP BY
Este caso es sutil: HAVING es legal incluso sin GROUP BY. La tabla completa se convierte en un único grupo implícito, y HAVING filtra ese grupo.
Si la condición de agregación es falsa, obtiene cero filas; si es verdadera, una fila. Es poco útil en la práctica, pero los entrevistadores lo preguntan para confirmar que entiende el concepto de grupo implícito.
-- Returns the count only if the table has > 100 rows
SELECT COUNT(*) AS total
FROM orders
HAVING COUNT(*) > 100;¿Puede HAVING usar un alias de SELECT?
Al igual que ocurre con el truco del ámbito de los alias en otros contextos, los dialectos difieren. Postgres y MySQL permiten que HAVING haga referencia a un alias de SELECT; SQL Server y Oracle no.
La práctica portable consiste en repetir la expresión de agregación en HAVING. Funciona en todos los motores y evita sorpresas en una entrevista sobre varias bases de datos.
-- Portable: repeat the aggregate, do not rely on the alias
SELECT region, SUM(amount) AS total
FROM sales
GROUP BY region
HAVING SUM(amount) > 5000;Enfoque desde el rendimiento
Para causar una buena impresión, relacione las cláusulas con el rendimiento: WHERE reduce las filas que el motor de agrupación debe explorar y puede utilizar índices; HAVING se ejecuta sobre grupos ya agregados, por lo que no puede reducir el coste de la agrupación.
La conclusión que esperan los entrevistadores es: aplique cada filtro lo antes posible. Solo las condiciones que dependen realmente de un agregado necesitan HAVING.
La respuesta en una sola frase
Memorice esto para la entrevista: «WHERE filtra las filas antes de la agrupación y no puede ver los agregados; HAVING filtra los grupos después de la agregación y es la única cláusula que puede comprobar el valor de un agregado».
Añada después la lista del orden de ejecución y habrá dado una respuesta completa, propia de una persona sénior.
Comprobación rápida
Decida a qué cláusula corresponde cada condición.
Resumen
WHERE: filtra las filas antes de GROUP BY; no permite funciones de agregación. HAVING: filtra los grupos después de la agregación; es el único lugar donde una condición sobre un agregado es legal.
- Coloque los filtros de columnas sin agregar en WHERE para mejorar la velocidad y aprovechar los índices.
- HAVING puede hacer referencia a columnas agrupadas, pero no debería utilizarse para filtros simples.
- HAVING funciona sin GROUP BY sobre el grupo implícito que representa toda la tabla.
- Repita las expresiones de agregación en HAVING para garantizar la compatibilidad entre dialectos.
Preguntas frecuentes
¿La lección «HAVING frente a WHERE» es gratis?
Sí — el texto completo de «HAVING frente a WHERE» es gratis para leer aquí en la web. Para practicarla de forma interactiva (editor de código integrado y tutor de IA 24/7) y desbloquear el resto del curso de SQL Interview Prep, actualiza a CoddyKit PRO. El curso de SQL Interview Prep incluye 4 lecciones en total.
¿Qué aprenderé en «HAVING frente a WHERE»?
Compare el filtrado antes y después de agrupar y determine qué cláusula puede ver la agregación Practicas SQL Interview Prep con código real que ejecutas directamente en el navegador, y un tutor de IA 24/7 responde tus preguntas mientras trabajas en la lección.
¿Necesito experiencia previa para empezar SQL Interview Prep?
No se requiere experiencia previa. SQL Interview Prep en CoddyKit está estructurado para principiantes hasta estudiantes avanzados, así que puedes empezar aquí o desde el inicio y avanzar a tu ritmo. Esta es la lección 2 de 4.
¿Cuánto tiempo toma la lección «HAVING frente a WHERE»?
La mayoría de las lecciones de CoddyKit toman alrededor de 5–10 minutos. Cada una es compacta e interactiva, así que avanzas constantemente y retomas exactamente por donde dejaste en la web y la app.
¿Puedo escribir y ejecutar código en esta lección de SQL Interview Prep?
Sí. Cada lección de SQL Interview Prep incluye un editor de código integrado, así que escribes y ejecutas código real directamente en tu navegador y obtienes retroalimentación instantánea de IA — sin configuración local necesaria.
Todas las lecciones de este curso
- La regla de GROUP BY para las columnas de SELECT
- HAVING frente a WHERE
- Agrupar por varias columnas y expresiones
- Contar y filtrar grupos