Jose Ricardo Heredia Avalos
Algo a considerar al usar $group es que los campos por los que usaras $group, vaya la redundancia, deben ir primero en $sort, ya que al usar estos dos, si importa que valor pusiste primero en $sort
El operador $group de MongoDB Aggregation Framework te permite agrupar documentos por un campo común y aplicar operaciones de acumulación sobre ellos, algo que el lenguaje estándar MongoDB Query Language no puede hacer por sí solo. Es una herramienta clave si trabajas con análisis de datos, reportes o segmentación de información dentro de colecciones grandes como las de Airbnb.
¿Qué hace el operador group en MongoDB?
El reto de esta práctica es claro: encontrar la propiedad más barata y la más cara dentro de cada tipo de propiedad (departamentos, casas, etc.) en Estados Unidos. Para resolverlo, necesitas combinar tres etapas dentro de un pipeline de agregación.
¿Qué es el operador $group? Es un operador de MongoDB Aggregation Framework que agrupa documentos según un campo común y permite aplicar acumuladores como
$first,$last,$sumo$avgsobre cada grupo.
¿Cómo se construye el pipeline paso a paso?
La consulta se arma en MongoDB Compass desde la pestaña aggregation, en modo texto. El orden importa, porque cada etapa recibe la salida de la anterior.
address.country_code.property_type y luego por price. Este truco es lo que después permite que $first y $last devuelvan el más barato y el más caro.Cada etapa va separada por coma y respeta sintaxis JSON estricta [02:15].
¿Cómo usar $first y $last para encontrar mínimos y máximos?
Dentro de $group, el campo _id define el ancla de agrupación. En este caso, _id: "$property_type" indica que MongoDB debe crear un grupo por cada tipo de propiedad.
Luego defines campos personalizados con acumuladores. Aquí entra la parte interesante: como ya ordenaste por precio ascendente, el primer documento de cada grupo es el más barato y el último es el más caro.
{ $group: { _id: "$property_type", masBajo: { $first: { nombre: "$name", precio: "$price", direccion: "$address" } }, masAlto: { $last: { nombre: "$name", precio: "$price", direccion: "$address" } } } }
El acumulador $first toma el primer elemento del grupo ordenado y $last toma el último. Así, en una sola etapa, obtienes ambos extremos del rango de precios [04:30].
¿Qué errores son comunes al escribir un $group?
Durante la práctica aparecen dos errores muy típicos que vale la pena tener identificados:
precio en lugar de $price rompe la consulta porque ese campo no existe en Airbnb.masBajo para crear masAlto, debes renombrar la clave, o terminarás con dos campos que dicen lo mismo pero contienen datos distintos.¿Por qué $group necesita un campo _id? Porque ese campo le dice a MongoDB sobre qué propiedad agrupar los documentos. Sin
_id, no hay agrupación posible.
¿Por qué $group no modifica la base de datos original?
Una de las grandes ventajas del Aggregation Framework es que todo el procesamiento ocurre dentro del pipeline, no sobre los documentos guardados. Tu colección original de Airbnb permanece intacta, y los resultados solo existen como salida temporal de la consulta.
Esto significa que puedes experimentar con distintas agrupaciones, acumuladores y combinaciones sin miedo a alterar los datos. Es ideal para análisis exploratorio, dashboards y reportes en tiempo real.
El resultado final muestra un documento por cada tipo de propiedad con dos objetos anidados: masBajo con la propiedad más económica y masAlto con la más cara, cada uno con su nombre, precio y dirección [06:45].
¿Qué otros acumuladores puedes explorar?
Más allá de $first y $last, el operador $group admite una familia amplia de acumuladores que vale la pena probar:
$sum para sumar valores numéricos dentro del grupo.$avg para calcular promedios, útil en análisis de precios medios.$min y $max para obtener directamente el valor mínimo o máximo sin necesidad de ordenar antes.$push y $addToSet para construir arrays con todos los valores del grupo.Cada uno responde a una pregunta de negocio distinta, y combinarlos dentro de un mismo $group te permite construir reportes muy completos en una sola consulta.
¿Has probado agrupar por más de un campo a la vez o combinar $group con $project? Cuéntanos en los comentarios qué experimentos te han funcionado mejor.
Aqui mi codigo usando $group
use("sample_airbnb") db.listingsAndReviews.aggregate( [ { $match:{ "address.country_code": "US", }, }, { $sort:{ property_type: 1, price: 1 }, }, { $group: { _id: "$property_type", "masBajo": { $first: { "nombre": "$name", "precio": "$price", "direccion": "$address" } }, "masAlto":{ $last: { "nombre": "$name", "precio": "$price", "direccion": "$address" } } } }, ] )
Jose Ricardo Heredia Avalos
Algo a considerar al usar $group es que los campos por los que usaras $group, vaya la redundancia, deben ir primero en $sort, ya que al usar estos dos, si importa que valor pusiste primero en $sort
Lourdes Montserrat González Gómez
Carlos Olivera Terrazas
ProfesorHola Lourdes,
Prueba con lo siguiente:
En la etapa $group, la clave _id debería tener el valor de $property_type en lugar de la cadena "property_type".
Cuando haces referencia a una llave del JSON de Aggregation Framework debes usar el prefijo "$" para que el intérprete entienda que no debe tratarlo como el contenido de una cadena de texto.
Emanuel Salazar
Los operadores de acumulación en MongoDB Aggregation Framework, como $sum, $avg, $min, $max y $push, sirven para realizar cálculos sobre un conjunto de documentos agrupados. Por ejemplo, $sum suma valores de un campo específico, mientras que $avg calcula el promedio. Estos operadores permiten extraer información valiosa y resumir grandes volúmenes de datos, facilitando análisis más profundos y decisiones estratégicas basadas en esos datos. Son esenciales para transformar información detallada en insights clave dentro de tus consultas.
Daniel Alfonso Barrera Adame
Como puedo convertir un string q esta mal guardado en un json, con una consulta y hacer un filtrado por una de sus subpropiedades ??
Gracias
Ronaldo Jiménez
Otro ejemplo:
Ronaldo Jiménez
// buscar la propiedad mas barata y la mas cara de cada tipo de propiedad en Estados Unidos // agrupar solo es posible con aggregation framework use("sample_airbnb") db.listingsAndReviews.aggregate([ { $match: {"address.country_code": "US"}, }, { $sort:{ "property_type": 1, "price": 1}, }, { $group: { _id: "$property_type", // agrupar por tipo de propiedad "masBajo": { $first: { // primer elemento (mas barato) "nombre": "$name", "precio": "$price" } }, "masAlto":{ $last: { // ultimo elemento (mas caro) "nombre": "$name", "precio": "$price" } } } }, ])
Hola! Alguien podría indicarme que estoy realizando mal?
use('sample_airbnb')
db.listingsAndReviews.aggregate([
{ $match: { "address.country_code" : "US" }}, {$sort: { property_type: 1, price: 1 }}, { $group: { _id: "property_type", masBajo: { $first: { // se obtiene el mas bajo nombre: "$name", precio: "$price", direccion: "$address" } }, masAlto: { $last: { // se obtiene el mas alto nombre: "$name", precio: "$price", direccion: "$address" } }, } }
])