## Punto 2: Extraer muestra aleatoria simple sin reemplazo de tamaño 110
df <- data.frame(peso = ChickWeight$weight, dieta = ChickWeight$Diet)


set.seed(123)  
muestra_simple <- df[sample(nrow(df), 110, replace = FALSE), ]

# Estimar media poblacional
media_muestra_simple <- mean(muestra_simple$peso)
media_poblacional <- mean(df$peso)
cat("Muestra Aleatoria Simple - Tamaño: 110\n")
## Muestra Aleatoria Simple - Tamaño: 110
cat("Media de la muestra:", round(media_muestra_simple, 2), "\n")
## Media de la muestra: 120.41
cat("Media poblacional real:", round(media_poblacional, 2), "\n")
## Media poblacional real: 121.82
cat("Error de estimación:", round(abs(media_muestra_simple - media_poblacional), 2), "\n\n")
## Error de estimación: 1.41
# Punto 3: Muestreo estratificado por dieta

estratos <- table(df$dieta)
cat("Distribución de la población por estratos (dieta):\n")
## Distribución de la población por estratos (dieta):
print(estratos)
## 
##   1   2   3   4 
## 220 120 120 118
cat("\n")
n_total <- 110


n_proporcional <- round((estratos / nrow(df)) * n_total)

cat("Asignación proporcional:\n")
## Asignación proporcional:
for(i in 1:4) {
  cat("Dieta", i, ": ", n_proporcional[i], " observaciones\n")
}
## Dieta 1 :  42  observaciones
## Dieta 2 :  23  observaciones
## Dieta 3 :  23  observaciones
## Dieta 4 :  22  observaciones
cat("\n")
muestras_proporcional <- list()
set.seed(123)

for(i in 1:4) {
  estrato_data <- df[df$dieta == i, ]
  muestras_proporcional[[i]] <- estrato_data[sample(nrow(estrato_data), n_proporcional[i], replace = FALSE), ]
}

# Asignación óptima (Neyman)

desv_estandar <- tapply(df$peso, df$dieta, sd)
tamanos_estratos <- tapply(df$peso, df$dieta, length)

cat("Desviaciones estándar por estrato:\n")
## Desviaciones estándar por estrato:
print(round(desv_estandar, 2))
##     1     2     3     4 
## 56.66 71.61 86.54 68.83
cat("\n")
producto_Ns <- tamanos_estratos * desv_estandar
suma_productos <- sum(producto_Ns)
n_optimo <- round((producto_Ns / suma_productos) * n_total)

diferencia <- n_total - sum(n_optimo)
if(diferencia != 0) {
  n_optimo[which.max(desv_estandar)] <- n_optimo[which.max(desv_estandar)] + diferencia
}

cat("Asignación óptima:\n")
## Asignación óptima:
for(i in 1:4) {
  cat("Dieta", i, ": ", n_optimo[i], " observaciones\n")
}
## Dieta 1 :  35  observaciones
## Dieta 2 :  24  observaciones
## Dieta 3 :  28  observaciones
## Dieta 4 :  23  observaciones
cat("\n")
muestras_optimo <- list()
set.seed(123)

for(i in 1:4) {
  estrato_data <- df[df$dieta == i, ]
  muestras_optimo[[i]] <- estrato_data[sample(nrow(estrato_data), n_optimo[i], replace = FALSE), ]
}

# Punto 4: Estimar medias poblacionales de los estratos

cat("ESTIMACIÓN DE MEDIAS POR ESTRATO\n")
## ESTIMACIÓN DE MEDIAS POR ESTRATO
cat("=================================\n\n")
## =================================
medias_reales <- tapply(df$peso, df$dieta, mean)

medias_proporcional <- sapply(muestras_proporcional, function(x) mean(x$peso))
medias_optimo <- sapply(muestras_optimo, function(x) mean(x$peso))

for(i in 1:4) {
  cat("Dieta", i, ":\n")
  cat("  Media real:", round(medias_reales[i], 2), "\n")
  cat("  Media proporcional:", round(medias_proporcional[i], 2), 
      " (Error:", round(abs(medias_proporcional[i] - medias_reales[i]), 2), ")\n")
  cat("  Media óptima:", round(medias_optimo[i], 2),
      " (Error:", round(abs(medias_optimo[i] - medias_reales[i]), 2), ")\n\n")
}
## Dieta 1 :
##   Media real: 102.65 
##   Media proporcional: 93.14  (Error: 9.5 )
##   Media óptima: 95.63  (Error: 7.02 )
## 
## Dieta 2 :
##   Media real: 122.62 
##   Media proporcional: 117.78  (Error: 4.83 )
##   Media óptima: 133.67  (Error: 11.05 )
## 
## Dieta 3 :
##   Media real: 142.95 
##   Media proporcional: 144.61  (Error: 1.66 )
##   Media óptima: 156.14  (Error: 13.19 )
## 
## Dieta 4 :
##   Media real: 135.26 
##   Media proporcional: 130.82  (Error: 4.44 )
##   Media óptima: 131.13  (Error: 4.13 )
# Punto 5: Estimar media poblacional general

cat("ESTIMACIÓN DE MEDIA POBLACIONAL GENERAL\n")
## ESTIMACIÓN DE MEDIA POBLACIONAL GENERAL
cat("=======================================\n\n")
## =======================================
media_real_general <- mean(df$peso)
media_proporcional_general <- sum(medias_proporcional * (tamanos_estratos / nrow(df)))

# Media con asignación óptima (ponderada por tamaño del estrato)
media_optimo_general <- sum(medias_optimo * (tamanos_estratos / nrow(df)))

cat("Media poblacional real:", round(media_real_general, 2), "\n")
## Media poblacional real: 121.82
cat("Media estimada (proporcional):", round(media_proporcional_general, 2),
    " (Error:", round(abs(media_proporcional_general - media_real_general), 2), ")\n")
## Media estimada (proporcional): 116.63  (Error: 5.18 )
cat("Media estimada (óptima):", round(media_optimo_general, 2),
    " (Error:", round(abs(media_optimo_general - media_real_general), 2), ")\n")
## Media estimada (óptima): 123.34  (Error: 1.52 )
cat("Media muestra simple:", round(media_muestra_simple, 2),
    " (Error:", round(abs(media_muestra_simple - media_real_general), 2), ")\n\n")
## Media muestra simple: 120.41  (Error: 1.41 )
# Resumen comparativo
cat("RESUMEN COMPARATIVO\n")
## RESUMEN COMPARATIVO
cat("===================\n")
## ===================
cat("Método más preciso para estimar media general:\n")
## Método más preciso para estimar media general:
errores <- c(
  "Proporcional" = abs(media_proporcional_general - media_real_general),
  "Óptima" = abs(media_optimo_general - media_real_general),
  "Simple" = abs(media_muestra_simple - media_real_general)
)

metodo_mejor <- names(errores)[which.min(errores)]
cat("->", metodo_mejor, "con error de", round(min(errores), 2), "\n")
## -> Simple con error de 1.41