# Librerías
library(kableExtra)
library(knitr)
library(magrittr)
library(dplyr)
##
## Adjuntando el paquete: 'dplyr'
## The following object is masked from 'package:kableExtra':
##
## group_rows
## The following objects are masked from 'package:stats':
##
## filter, lag
## The following objects are masked from 'package:base':
##
## intersect, setdiff, setequal, union
library(e1071)
# Cargar datos
datos <- read.csv("china_water_pollution_data.csv",
header = TRUE,
sep = ",",
dec = ".")
Turbidez <- datos$Turbidity_NTU
Turbidez <- na.omit(Turbidez)
Turbidez <- Turbidez[Turbidez >= 0]
n <- length(Turbidez)
n
## [1] 3000
# 1. Asegurar que Nitrito sea un vector limpio y numérico
Turbidez <- as.numeric(na.omit(datos$Turbidity_NTU))
Turbidez <- Turbidez[Turbidez >= 0]
n_total <- length(Turbidez) # Esto debe ser 3000
# 2. Definir parámetros
minimo <- min(Turbidez)
maximo <- max(Turbidez)
K <- floor(1 + 3.322 * log10(n_total))
# 3. EL TRUCO DEFINITIVO PARA LOS 3000:
# Creamos los cortes pero expandimos los extremos
# para que el mínimo y el máximo REALES queden adentro del rango.
rango_ajustado <- seq(from = minimo - 0.001, to = maximo + 0.001, length.out = K + 1)
# 4. Generar la tabla de frecuencias
# 'include.lowest = TRUE' es vital para que el primer dato entre
intervalos <- cut(Turbidez, breaks = rango_ajustado, include.lowest = TRUE, right = TRUE)
tabla_base <- table(intervalos)
ni <- as.numeric(tabla_base)
# 5. Verificación de seguridad (Si falta algo, se suma a la última clase)
if(sum(ni) != n_total){
diferencia <- n_total - sum(ni)
ni[length(ni)] <- ni[length(ni)] + diferencia
}
# 6. Construcción de la tabla final
Li <- rango_ajustado[-length(rango_ajustado)]
Ls <- rango_ajustado[-1]
Mc <- (Li + Ls)/2
hi <- (ni / sum(ni)) * 100
Ni_asc <- cumsum(ni)
Hi_asc <- cumsum(hi)
TDF_Turbidez <- data.frame(
Lim_inf = Li,
Lim_sup = Ls,
MC = Mc,
ni = ni,
hi = hi,
Ni_asc = Ni_asc,
Hi_asc = Hi_asc
)
# 7. Mostrar con kable
library(knitr)
library(kableExtra)
kable(TDF_Turbidez,
digits = 3,
align = "c",
col.names = c("Lím. Inf.", "Lím. Sup.", "MC", "ni", "hi (%)", "Ni Asc.", "Hi Asc. (%)"),
caption = paste("TABLA FINAL - TOTAL DATOS:", sum(ni))) %>%
kable_styling(full_width = FALSE, bootstrap_options = c("striped", "hover"))
| Lím. Inf. | Lím. Sup. | MC | ni | hi (%) | Ni Asc. | Hi Asc. (%) |
|---|---|---|---|---|---|---|
| -0.001 | 3.956 | 1.977 | 1653 | 55.100 | 1653 | 55.100 |
| 3.956 | 7.913 | 5.934 | 734 | 24.467 | 2387 | 79.567 |
| 7.913 | 11.869 | 9.891 | 333 | 11.100 | 2720 | 90.667 |
| 11.869 | 15.826 | 13.848 | 155 | 5.167 | 2875 | 95.833 |
| 15.826 | 19.783 | 17.805 | 78 | 2.600 | 2953 | 98.433 |
| 19.783 | 23.740 | 21.762 | 28 | 0.933 | 2981 | 99.367 |
| 23.740 | 27.697 | 25.718 | 9 | 0.300 | 2990 | 99.667 |
| 27.697 | 31.654 | 29.675 | 6 | 0.200 | 2996 | 99.867 |
| 31.654 | 35.610 | 33.632 | 2 | 0.067 | 2998 | 99.933 |
| 35.610 | 39.567 | 37.589 | 0 | 0.000 | 2998 | 99.933 |
| 39.567 | 43.524 | 41.546 | 1 | 0.033 | 2999 | 99.967 |
| 43.524 | 47.481 | 45.503 | 1 | 0.033 | 3000 | 100.000 |
La tabla de distribución de frecuencia de la Turbidez fue construida inicialmente aplicando la Regla de Sturges para determinar el número óptimo de clases.
Posteriormente, el procedimiento se simplificó utilizando la función hist(), obteniendo automáticamente los intervalos y frecuencias, confirmando los resultados obtenidos manualmente.
Hist_Turbidez <- hist(Turbidez,
breaks = K,
plot = FALSE)
Li <- Hist_Turbidez$breaks[-length(Hist_Turbidez$breaks)]
Ls <- Hist_Turbidez$breaks[-1]
ni <- Hist_Turbidez$counts
hi <- round((ni/sum(ni))*100,2)
TDF_simplificada <- data.frame(
Lim_inf = round(Li,2),
Lim_sup = round(Ls,2),
ni = ni,
hi = hi
)
kable(TDF_simplificada,
align="c",
caption="Tabla simplificada obtenida mediante hist()")
| Lim_inf | Lim_sup | ni | hi |
|---|---|---|---|
| 0 | 5 | 1911 | 63.70 |
| 5 | 10 | 678 | 22.60 |
| 10 | 15 | 272 | 9.07 |
| 15 | 20 | 94 | 3.13 |
| 20 | 25 | 32 | 1.07 |
| 25 | 30 | 6 | 0.20 |
| 30 | 35 | 4 | 0.13 |
| 35 | 40 | 1 | 0.03 |
| 40 | 45 | 1 | 0.03 |
| 45 | 50 | 1 | 0.03 |
hist(Turbidez, breaks = 10,
main = "Gráfica N°1: Distribución de la Turbidez
en el estudio de contaminación del agua
en China en el año 2023",
xlab = "Turbidez (NTU)",
ylab = "Cantidad",
ylim = c(0, max(ni)),
col = "lightgreen")
hist(Turbidez, breaks = 10,
main = "Gráfica N°2: Distribución general de la Turbidez
en el estudio de contaminación del agua en China 2023",
xlab = "Turbidez (NTU)",
ylab = "Cantidad",
ylim = c(0, max(ni)),
col = "lightgreen")
barplot(
height = TDF_Turbidez$hi,
space = 0,
col = "skyblue",
main = "Gráfica N°3: Distribución porcentual de la Turbidez\nen el estudio de contaminación del agua en China 2023",
xlab = "Turbidez (NTU)",
ylab = "Porcentaje (%)",
names.arg = TDF_Turbidez$MC,
ylim = c(0, max(TDF_Turbidez$hi) + 10) # Ajuste automático del eje Y
)
boxplot(Turbidez,
horizontal = TRUE,
main = "Gráfica N°6: Diagrama de caja de la Turbidez
en el estudio de contaminación del agua en China 2023",
xlab = "Turbidez (NTU)",
col = "green",
outline = TRUE)
summary(Turbidez)
## Min. 1st Qu. Median Mean 3rd Qu. Max.
## 0.000 1.430 3.445 4.948 6.933 47.480
Ni_asc <- cumsum(ni)
Ni_desc <- rev(cumsum(rev(ni)))
plot(Ls, Ni_asc,
type = "o",
col = "orange",
lwd = 3,
xlab = "Turbidez (NTU)",
ylab = "Frecuencia acumulada",
main = "Gráfica N°7: Ojiva Ascendente y Descendente")
lines(Li, Ni_desc,
type = "o",
col = "green",
lwd = 3)
Hi_asc <- cumsum(hi)
Hi_desc <- rev(cumsum(rev(hi)))
plot(Ls, Hi_asc,
type = "o",
col = "blue",
lwd = 3,
xlab = "Turbidez (NTU)",
ylab = "Porcentaje acumulado (%)",
main = "Gráfica N°8: Ojiva porcentual Ascendente y Descendente")
lines(Li, Hi_desc,
type = "o",
col = "red",
lwd = 3)
media <- round(mean(Turbidez),2)
mediana <- median(Turbidez)
max_ni <- max(TDF_Turbidez$ni)
moda <- TDF_Turbidez$MC[TDF_Turbidez$ni == max_ni]
media
## [1] 4.95
mediana
## [1] 3.445
moda
## [1] 1.977417
varianza <- var(Turbidez)
sd <- sd(Turbidez)
cv <- round((sd/media)*100,2)
varianza
## [1] 24.11285
sd
## [1] 4.910484
cv
## [1] 99.2
library(e1071)
asimetria <- skewness(Turbidez, type = 2)
curtosis <- kurtosis(Turbidez)
asimetria
## [1] 1.959997
curtosis
## [1] 6.067872
tabla_indicadores <- data.frame(
"Variable" = "Turbidez (NTU)",
"Rango" = paste0("[",min(Turbidez),";",max(Turbidez),"]"),
"X" = media,
"Me" = round(mediana,2),
"Mo" = moda,
"V" = round(varianza,2),
"Sd" = round(sd,2),
"Cv" = cv,
"As" = round(asimetria,2),
"K" = round(curtosis,2)
)
kable(tabla_indicadores, align='c',
caption="Conclusiones de la variable Turbidez (NTU)")
| Variable | Rango | X | Me | Mo | V | Sd | Cv | As | K |
|---|---|---|---|---|---|---|---|---|---|
| Turbidez (NTU) | [0;47.48] | 4.95 | 3.45 | 1.977417 | 24.11 | 4.91 | 99.2 | 1.96 | 6.07 |
La variable Turbidez (NTU) fluctúa entre 0 y 47.48 NTU, y sus valores giran en torno a 4.95 NTU, con una desviación estándar de 4.91 NTU, siendo un conjunto de datos con variabilidad alta (CV = 99.2%). Los valores se distribuyen de manera asimétrica hacia valores mayores (As ≈ 1.96), indicando que hay presencia de mediciones relativamente elevadas en comparación con la media, y presentan una curtosis muy positiva (K = 6.07), evidenciando una distribución con colas pesadas y valores extremos significativos. Por lo anterior, el comportamiento de la variable Turbidez (NTU) refleja una alta dispersión de los datos, con algunos valores extremos, lo que debe considerarse en el análisis de la calidad del agua en China durante el año 2023.