ACTIVIDAD 121 - CASO 1: INDICADORES ESTADÍSTICOS

Análisis descriptivo de la base de datos de cervezas

Jacobo Raffan Perez

07 de agosto de 2026

1. INTRODUCCIÓN

Este informe calcula los indicadores estadísticos correspondientes a los dos videos de apoyo de la actividad. El primero corresponde a indicadores calculados sobre datos individuales: n, mínimo, máximo, media, mediana, cuartiles, rango, varianza, desviación estándar, coeficiente de variación, coeficiente de asimetría y coeficiente de curtosis. El segundo corresponde a esos mismos indicadores calculados a partir de una tabla de distribución de frecuencias por intervalos, usando interpolación lineal. Todos los cálculos se aplican sobre la base de datos beer2.csv, compuesta por 1.586.614 registros de cervezas.

2. CARGA Y EXPLORACIÓN DE LOS DATOS

library(data.table)

cerveza <- fread("beer2.csv")

dim(cerveza)
## [1] 1586614      15
str(cerveza)
## Classes 'data.table' and 'data.frame':   1586614 obs. of  15 variables:
##  $ id            : int  47986 48213 48215 47969 64883 52159 52159 52159 52159 52159 ...
##  $ marca         : chr  "Vecchio Birraio" "Vecchio Birraio" "Vecchio Birraio" "Vecchio Birraio" ...
##  $ precio        : num  4.99 4.45 4.95 5.58 3.9 5.07 5.07 5.07 5.07 5.07 ...
##  $ alcohol       : num  13.8 16.9 17.7 13.8 20.7 ...
##  $ carbohidratos : num  11.5 14.2 15 10.5 15.2 12.1 12.1 12.1 12.1 12.1 ...
##  $ calorias      : int  148 181 190 144 212 145 145 145 145 145 ...
##  $ nacionalidad  : chr  "Canadá" "Canadá" "Canadá" "Canadá" ...
##  $ calificacion  : num  1.5 3 3 3 4 3 3.5 3 4 4.5 ...
##  $ aroma         : num  2 2.5 2.5 3 4.5 3.5 3.5 2.5 3 3.5 ...
##  $ apariencia    : num  2.5 3 3 3.5 4 3.5 3.5 3.5 3.5 5 ...
##  $ paladar       : num  1.5 3 3 2.5 4 3 4 2 3.5 4 ...
##  $ sabor         : num  1.5 3 3 3 4.5 3.5 4 3.5 4 4 ...
##  $ nombre_cerveza: chr  "Sausa Weizen" "Red Moon" "Black Horse Black Beer" "Sausa Pils" ...
##  $ tipo          : chr  "clara artesanal" "cerveza normal y helada" "cerveza normal y helada" "lager importada" ...
##  $ origen        : chr  "importada" "importada" "importada" "importada" ...
##  - attr(*, ".internal.selfref")=<pointer: 0x000001d5a014d900>
summary(cerveza)
##        id              marca             precio        alcohol     
##  Min.   :    3   Length   :1586614   Min.   :2.37   Min.   : 0.03  
##  1st Qu.: 1717   N.unique :   5743   1st Qu.:4.36   1st Qu.:14.28  
##  Median :13906   N.blank  :      0   Median :5.00   Median :17.67  
##  Mean   :21713   Min.nchar:      3   Mean   :5.00   Mean   :18.71  
##  3rd Qu.:39441   Max.nchar:     66   3rd Qu.:5.64   3rd Qu.:22.63  
##  Max.   :77317                       Max.   :7.72   Max.   :59.45  
##  carbohidratos      calorias        nacionalidad      calificacion  
##  Min.   : 3.50   Min.   : 21.0   Length   :1586614   Min.   :0.000  
##  1st Qu.:12.40   1st Qu.:157.0   N.unique :     10   1st Qu.:3.500  
##  Median :13.80   Median :182.0   N.blank  :      0   Median :4.000  
##  Mean   :14.05   Mean   :193.2   Min.nchar:      5   Mean   :3.816  
##  3rd Qu.:15.60   3rd Qu.:224.0   Max.nchar:     15   3rd Qu.:4.500  
##  Max.   :30.20   Max.   :541.0                       Max.   :5.000  
##      aroma         apariencia       paladar          sabor      
##  Min.   :1.000   Min.   :0.000   Min.   :1.000   Min.   :1.000  
##  1st Qu.:3.500   1st Qu.:3.500   1st Qu.:3.500   1st Qu.:3.500  
##  Median :4.000   Median :4.000   Median :4.000   Median :4.000  
##  Mean   :3.736   Mean   :3.842   Mean   :3.744   Mean   :3.793  
##  3rd Qu.:4.000   3rd Qu.:4.000   3rd Qu.:4.000   3rd Qu.:4.500  
##  Max.   :5.000   Max.   :5.000   Max.   :5.000   Max.   :5.000  
##    nombre_cerveza           tipo               origen       
##  Length   :1586614   Length   :1586614   Length   :1586614  
##  N.unique :  56857   N.unique :      5   N.unique :      2  
##  N.blank  :      0   N.blank  :      0   N.blank  :      0  
##  Min.nchar:      1   Min.nchar:     15   Min.nchar:      8  
##  Max.nchar:     76   Max.nchar:     30   Max.nchar:      9  
## 

Las variables cuantitativas de la base son: precio, alcohol, carbohidratos, calorías, calificación, aroma, apariencia, paladar y sabor.

3. INDICADORES SOBRE DATOS INDIVIDUALES

calcular_indicadores <- function(x) {
  n        <- length(x)
  minimo   <- min(x)
  maximo   <- max(x)
  media    <- mean(x)
  mediana  <- median(x)
  q1       <- as.numeric(quantile(x, 0.25))
  q3       <- as.numeric(quantile(x, 0.75))
  rango    <- maximo - minimo
  varianza <- var(x)
  desv_est <- sd(x)
  cv       <- (desv_est / media) * 100
  asimetria <- (sum((x - media)^3) / n) / (desv_est^3)
  curtosis <- (sum((x - media)^4) / n) / (desv_est^4) - 3

  data.frame(
    n = n, minimo = minimo, maximo = maximo, media = media,
    mediana = mediana, Q1 = q1, Q3 = q3, rango = rango,
    varianza = varianza, desviacion = desv_est, CV_pct = cv,
    asimetria = asimetria, curtosis = curtosis
  )
}
variables_numericas <- c("precio", "alcohol", "carbohidratos", "calorias",
                          "calificacion", "aroma", "apariencia",
                          "paladar", "sabor")

resumen_indicadores <- do.call(rbind, lapply(variables_numericas, function(v) {
  res <- calcular_indicadores(cerveza[[v]])
  res$variable <- v
  res
}))

resumen_indicadores <- resumen_indicadores[, c("variable",
                          setdiff(names(resumen_indicadores), "variable"))]

knitr::kable(resumen_indicadores, digits = 3,
             caption = "Indicadores estadísticos por variable")
Indicadores estadísticos por variable
variable n minimo maximo media mediana Q1 Q3 rango varianza desviacion CV_pct asimetria curtosis
precio 1586614 2.37 7.72 5.000 5.00 4.36 5.64 5.35 0.784 0.885 17.708 0.000 -0.500
alcohol 1586614 0.03 59.45 18.712 17.67 14.28 22.63 59.42 29.768 5.456 29.158 0.959 1.310
carbohidratos 1586614 3.50 30.20 14.048 13.80 12.40 15.60 26.70 5.645 2.376 16.913 0.461 0.869
calorias 1586614 21.00 541.00 193.173 182.00 157.00 224.00 520.00 2168.646 46.569 24.107 0.915 1.318
calificacion 1586614 0.00 5.00 3.816 4.00 3.50 4.50 5.00 0.519 0.721 18.886 -1.024 1.631
aroma 1586614 1.00 5.00 3.736 4.00 3.50 4.00 4.00 0.487 0.698 18.675 -0.839 1.145
apariencia 1586614 0.00 5.00 3.842 4.00 3.50 4.00 5.00 0.380 0.616 16.037 -0.902 1.739
paladar 1586614 1.00 5.00 3.744 4.00 3.50 4.00 4.00 0.465 0.682 18.223 -0.869 1.303
sabor 1586614 1.00 5.00 3.793 4.00 3.50 4.50 4.00 0.536 0.732 19.299 -0.973 1.342

INTERPRETACIÓN

El precio tiene una media de 5.00 y una mediana de 5.00, casi iguales, y un coeficiente de asimetría muy cercano a cero (-0.0004), lo que quiere decir que los datos están repartidos de forma pareja a ambos lados de la media. Su curtosis negativa (-0.50) muestra una distribución plana, sin un punto donde se junten muchos datos.

El alcohol es la variable con más variabilidad (CV = 29.16%) y con la asimetría positiva más alta (0.96). Esto significa que la mayoría de las cervezas tienen un grado de alcohol moderado, pero hay un grupo de cervezas con mucho más alcohol que las demás, y eso alarga la distribución hacia la derecha. Su curtosis positiva (1.31) indica que los datos están más juntos alrededor de la media que en una distribución normal.

Las calorías se comportan de forma parecida al alcohol: tienen una variabilidad alta (CV = 24.11%) y asimetría positiva (0.92). Esto tiene sentido porque las cervezas con más alcohol suelen tener también más calorías.

Los carbohidratos tienen una variabilidad media (CV = 16.91%) y una asimetría positiva baja (0.46), es decir, sus datos están bastante equilibrados, con muy pocos valores altos que se alejan del resto.

Las cinco variables de calificación (calificación, aroma, apariencia, paladar y sabor) se comportan parecido entre sí: todas tienen asimetría negativa (entre -0.84 y -1.02). Esto muestra que la mayoría de las cervezas reciben calificaciones altas (entre 3.5 y 4.5 sobre 5), y solo unas pocas reciben calificaciones bajas. Todas tienen también curtosis positiva, y apariencia es la que tiene los datos más juntos (1.74) y la menor variabilidad (CV = 16.04%), o sea, es la calificación en la que más se ponen de acuerdo los evaluadores. En cambio, calificación general es la que tiene más variabilidad (CV = 18.89%) y la asimetría negativa más fuerte (-1.02).

4. TABLA DE DISTRIBUCIÓN DE FRECUENCIAS E INDICADORES AGRUPADOS

Esta sección trabaja con la variable precio.

variable_agrupada <- "precio"
x <- cerveza[[variable_agrupada]]
n <- length(x)

k <- ceiling(1 + 3.322 * log10(n))

rango    <- max(x) - min(x)
amplitud <- rango / k

limites <- seq(min(x), max(x), by = amplitud)
limites[length(limites)] <- max(x) + 1e-9

intervalos <- cut(x, breaks = limites, right = FALSE, include.lowest = TRUE)

tabla <- as.data.frame(table(intervalos))
names(tabla) <- c("intervalo", "ni")

tabla$Li <- limites[-length(limites)]
tabla$Ls <- limites[-1]
tabla$xi <- (tabla$Li + tabla$Ls) / 2

tabla$hi <- tabla$ni / n
tabla$Ni <- cumsum(tabla$ni)
tabla$Hi <- cumsum(tabla$hi)

knitr::kable(tabla[, c("intervalo", "Li", "Ls", "xi", "ni", "hi", "Ni", "Hi")],
             digits = 4,
             caption = paste("Tabla de distribución de frecuencias -", variable_agrupada))
Tabla de distribución de frecuencias - precio
intervalo Li Ls xi ni hi Ni Hi
[2.37,2.61) 2.3700 2.6132 2.4916 674 0.0004 674 0.0004
[2.61,2.86) 2.6132 2.8564 2.7348 4067 0.0026 4741 0.0030
[2.86,3.1) 2.8564 3.0995 2.9780 12118 0.0076 16859 0.0106
[3.1,3.34) 3.0995 3.3427 3.2211 27506 0.0173 44365 0.0280
[3.34,3.59) 3.3427 3.5859 3.4643 45047 0.0284 89412 0.0564
[3.59,3.83) 3.5859 3.8291 3.7075 68328 0.0431 157740 0.0994
[3.83,4.07) 3.8291 4.0723 3.9507 97011 0.0611 254751 0.1606
[4.07,4.32) 4.0723 4.3155 4.1939 116909 0.0737 371660 0.2342
[4.32,4.56) 4.3155 4.5586 4.4370 136622 0.0861 508282 0.3204
[4.56,4.8) 4.5586 4.8018 4.6802 156811 0.0988 665093 0.4192
[4.8,5.04) 4.8018 5.0450 4.9234 157873 0.0995 822966 0.5187
[5.04,5.29) 5.0450 5.2882 5.1666 155878 0.0982 978844 0.6169
[5.29,5.53) 5.2882 5.5314 5.4098 152753 0.0963 1131597 0.7132
[5.53,5.77) 5.5314 5.7745 5.6530 130084 0.0820 1261681 0.7952
[5.77,6.02) 5.7745 6.0177 5.8961 108164 0.0682 1369845 0.8634
[6.02,6.26) 6.0177 6.2609 6.1393 87416 0.0551 1457261 0.9185
[6.26,6.5) 6.2609 6.5041 6.3825 59394 0.0374 1516655 0.9559
[6.5,6.75) 6.5041 6.7473 6.6257 37819 0.0238 1554474 0.9797
[6.75,6.99) 6.7473 6.9905 6.8689 21128 0.0133 1575602 0.9931
[6.99,7.23) 6.9905 7.2336 7.1120 8446 0.0053 1584048 0.9984
[7.23,7.48) 7.2336 7.4768 7.3552 2327 0.0015 1586375 0.9998
[7.48,7.72] 7.4768 7.7200 7.5984 239 0.0002 1586614 1.0000

Con una base de 1.586.614 datos, la regla de Sturges arroja 22 intervalos de amplitud aproximada 0.243, cubriendo el rango de precios entre 2.37 y 7.72.

4.1 MEDIA AGRUPADA

\[\bar{x} = \sum x_i \cdot h_i\]

media_agrupada <- sum(tabla$xi * tabla$hi)
media_agrupada
## [1] 5.000018

4.2 VARIANZA MUESTRAL AGRUPADA

\[S^2 = \frac{\sum n_i (x_i - \bar{x})^2}{n - 1}\]

varianza_agrupada <- sum(tabla$ni * (tabla$xi - media_agrupada)^2) / (n - 1)
varianza_agrupada
## [1] 0.7880641
sqrt(varianza_agrupada)
## [1] 0.8877298

4.3 MEDIANA AGRUPADA

calcular_percentil_agrupado <- function(tabla, n, p) {
  objetivo <- p * n
  fila <- which(tabla$Ni >= objetivo)[1]

  Li  <- tabla$Li[fila]
  Ls  <- tabla$Ls[fila]
  amp <- Ls - Li
  ni  <- tabla$ni[fila]
  N_anterior <- ifelse(fila == 1, 0, tabla$Ni[fila - 1])

  Li + ((objetivo - N_anterior) / ni) * amp
}

mediana_agrupada <- calcular_percentil_agrupado(tabla, n, 0.5)
mediana_agrupada
## [1] 4.999314

4.4 CUARTILES AGRUPADOS

Q1_agrupado <- calcular_percentil_agrupado(tabla, n, 0.25)
Q3_agrupado <- calcular_percentil_agrupado(tabla, n, 0.75)

data.frame(Q1 = Q1_agrupado, Q3 = Q3_agrupado)
##         Q1      Q3
## 1 4.359942 5.64047

4.5 PORCENTAJE DE DATOS POR DEBAJO DE LA MEDIA

valor_referencia <- media_agrupada

calcular_pct_menor_que <- function(tabla, n, valor) {
  fila <- which(tabla$Li <= valor & valor < tabla$Ls)[1]

  Li  <- tabla$Li[fila]
  Ls  <- tabla$Ls[fila]
  amp <- Ls - Li
  ni  <- tabla$ni[fila]
  N_anterior <- ifelse(fila == 1, 0, tabla$Ni[fila - 1])

  N_valor <- N_anterior + ((valor - Li) / amp) * ni
  N_valor / n
}

proporcion <- calcular_pct_menor_que(tabla, n, valor_referencia)
proporcion
## [1] 0.5002881
proporcion * 100
## [1] 50.02881

El 50.03% de las cervezas tienen un precio menor al precio promedio (5.00). Esto va de acuerdo con lo que ya se vio antes: la variable precio está muy bien repartida, casi sin inclinarse hacia ningún lado.

4.6 HISTOGRAMA DE LA DISTRIBUCIÓN

hist(x, breaks = limites, col = "steelblue", border = "white",
     main = paste("Distribución de", variable_agrupada),
     xlab = variable_agrupada, ylab = "Frecuencia absoluta")
abline(v = media_agrupada, col = "red", lwd = 2, lty = 2)
legend("topright", legend = "Media", col = "red", lty = 2, lwd = 2)

El histograma confirma lo que ya se vio con la asimetría y la curtosis: la distribución del precio es plana y bastante pareja, sin un intervalo que tenga muchas más cervezas que los demás.

5. COMPARACIÓN: DATOS INDIVIDUALES VS. DATOS AGRUPADOS

individuales <- resumen_indicadores[resumen_indicadores$variable == variable_agrupada, ]

comparacion <- data.frame(
  indicador = c("Media", "Mediana", "Q1", "Q3", "Varianza"),
  datos_individuales = c(individuales$media, individuales$mediana,
                          individuales$Q1, individuales$Q3, individuales$varianza),
  datos_agrupados = c(media_agrupada, mediana_agrupada,
                       Q1_agrupado, Q3_agrupado, varianza_agrupada)
)

knitr::kable(comparacion, digits = 4,
             caption = "Comparación de indicadores: individuales vs. agrupados")
Comparación de indicadores: individuales vs. agrupados
indicador datos_individuales datos_agrupados
Media 5.000 5.0000
Mediana 5.000 4.9993
Q1 4.360 4.3599
Q3 5.640 5.6405
Varianza 0.784 0.7881

Los resultados con datos individuales y con datos agrupados son casi iguales: la media pasa de 5.0000 a 5.0000, la mediana de 5.0000 a 4.9993, el primer cuartil de 4.3600 a 4.3599, el tercer cuartil de 5.6400 a 5.6405, y la varianza de 0.7840 a 0.7881. Las pequeñas diferencias se dan porque el método agrupado supone que los datos se reparten igual dentro de cada intervalo, mientras que el cálculo individual usa cada dato tal cual es. Que los dos métodos den resultados tan parecidos muestra que la tabla de distribución de frecuencias (con 22 intervalos y más de 1.5 millones de datos) refleja bien el comportamiento real de la variable.

6. CONCLUSIONES

El precio es la variable más pareja y bien repartida de la base de datos, con una variabilidad moderada (CV = 17.71%) y sin inclinarse hacia ningún lado, lo que sugiere que los precios entre marcas y orígenes no varían demasiado. El alcohol y las calorías, en cambio, son las que más varían y las que más se inclinan hacia valores altos, lo que muestra que existe un grupo de cervezas fuertes y con muchas calorías que se aleja del resto. Las variables de calificación (calificación, aroma, apariencia, paladar y sabor) siempre se inclinan hacia valores bajos en su asimetría, lo que quiere decir que la mayoría de las cervezas reciben notas altas, entre 3.5 y 4.5, y son pocas las que reciben notas bajas. Apariencia es la calificación en la que más se ponen de acuerdo los evaluadores, mientras que calificación general es en la que más varían las opiniones. Por último, al comparar el cálculo hecho con los datos individuales y el hecho con datos agrupados para el precio, los resultados salieron casi iguales, con diferencias muy pequeñas que se deben solo a que trabajar con intervalos es menos exacto que trabajar con cada dato por separado.