Librerías necesarias para el estudio

library(readxl)
library(ggplot2)
library(dplyr)
## 
## Adjuntando el paquete: 'dplyr'
## The following objects are masked from 'package:stats':
## 
##     filter, lag
## The following objects are masked from 'package:base':
## 
##     intersect, setdiff, setequal, union
library(tibble)
library(base)
library(Amelia)
## Cargando paquete requerido: Rcpp
## ## 
## ## Amelia II: Multiple Imputation
## ## (Version 1.8.3, built: 2024-11-07)
## ## Copyright (C) 2005-2025 James Honaker, Gary King and Matthew Blackwell
## ## Refer to http://gking.harvard.edu/amelia/ for more information
## ##
library(EnvStats)
## 
## Adjuntando el paquete: 'EnvStats'
## The following objects are masked from 'package:stats':
## 
##     predict, predict.lm
## The following object is masked from 'package:base':
## 
##     print.default
library(nortest)
library(corrplot)
## corrplot 0.95 loaded
library(gridExtra)
## 
## Adjuntando el paquete: 'gridExtra'
## The following object is masked from 'package:dplyr':
## 
##     combine
library(MASS) 
## 
## Adjuntando el paquete: 'MASS'
## The following object is masked from 'package:EnvStats':
## 
##     boxcox
## The following object is masked from 'package:dplyr':
## 
##     select
library(corrplot)
library(tidyverse)  
## ── Attaching core tidyverse packages ──────────────────────── tidyverse 2.0.0 ──
## ✔ forcats   1.0.0     ✔ readr     2.1.5
## ✔ lubridate 1.9.4     ✔ stringr   1.5.1
## ✔ purrr     1.1.0     ✔ tidyr     1.3.1
## ── Conflicts ────────────────────────────────────────── tidyverse_conflicts() ──
## ✖ gridExtra::combine() masks dplyr::combine()
## ✖ dplyr::filter()      masks stats::filter()
## ✖ dplyr::lag()         masks stats::lag()
## ✖ MASS::select()       masks dplyr::select()
## ℹ Use the conflicted package (<http://conflicted.r-lib.org/>) to force all conflicts to become errors
library(tidyr)
library(GGally)

Datos horarios de radiación y variables meteorológicas para análisis de salud cutánea y edificaciones sostenibles en Chía, Cundinamarca (NASA POWER)

datos <- read.csv("C:/Users/Administrador/Downloads/DATASET_PROY_OFICIAL.csv",
                      sep=",",header=TRUE,
                      fileEncoding = "UTF-8")

Naturaleza de los datos

head(datos)
##   YEAR MO DY HR ALLSKY_SFC_UVB ALLSKY_SFC_LW_DWN PRECTOTCORR    PS
## 1 2025  1  1  0              0            370.20        0.48 84.53
## 2 2025  1  1  1              0            372.25        0.49 84.48
## 3 2025  1  1  2              0            363.10        0.53 84.44
## 4 2025  1  1  3              0            367.58        0.48 84.43
## 5 2025  1  1  4              0            366.67        0.37 84.43
## 6 2025  1  1  5              0            365.10        0.30 84.47
tail(datos)
##      YEAR MO DY HR ALLSKY_SFC_UVB ALLSKY_SFC_LW_DWN PRECTOTCORR   PS
## 5131 2025  8  2 18           -999              -999        -999 -999
## 5132 2025  8  2 19           -999              -999        -999 -999
## 5133 2025  8  2 20           -999              -999        -999 -999
## 5134 2025  8  2 21           -999              -999        -999 -999
## 5135 2025  8  2 22           -999              -999        -999 -999
## 5136 2025  8  2 23           -999              -999        -999 -999
dim(datos)
## [1] 5136    8
colnames(datos)
## [1] "YEAR"              "MO"                "DY"               
## [4] "HR"                "ALLSKY_SFC_UVB"    "ALLSKY_SFC_LW_DWN"
## [7] "PRECTOTCORR"       "PS"
summary(datos)
##       YEAR            MO              DY              HR       
##  Min.   :2025   Min.   :1.000   Min.   : 1.00   Min.   : 0.00  
##  1st Qu.:2025   1st Qu.:2.000   1st Qu.: 8.00   1st Qu.: 5.75  
##  Median :2025   Median :4.000   Median :15.50   Median :11.50  
##  Mean   :2025   Mean   :4.056   Mean   :15.53   Mean   :11.50  
##  3rd Qu.:2025   3rd Qu.:6.000   3rd Qu.:23.00   3rd Qu.:17.25  
##  Max.   :2025   Max.   :8.000   Max.   :31.00   Max.   :23.00  
##  ALLSKY_SFC_UVB    ALLSKY_SFC_LW_DWN  PRECTOTCORR             PS         
##  Min.   :-999.00   Min.   :-999.0    Min.   :-999.000   Min.   :-999.00  
##  1st Qu.:-999.00   1st Qu.:-999.0    1st Qu.:   0.550   1st Qu.:  84.39  
##  Median :   0.00   Median : 366.5    Median :   2.420   Median :  84.54  
##  Mean   :-443.27   Mean   :-227.9    Mean   :  -6.914   Mean   :  69.21  
##  3rd Qu.:   0.01   3rd Qu.: 389.4    3rd Qu.:   6.970   3rd Qu.:  84.65  
##  Max.   :   2.21   Max.   : 436.5    Max.   : 455.330   Max.   :  84.93

YEAR → Año del registro.

MO → Mes del registro.

DY → Día del registro.

HR → Hora del registro (horario local o UTC).

ALLSKY_SFC_UVB → Irradiancia UVB en superficie bajo cielo total en W/m².

ALLSKY_SFC_LW_DWN → Irradiancia de onda larga descendente en superficie bajo cielo total en W/m².

PRECTOTCORR → Precipitación total corregida en mm/h.

PS → Presión superficial en kPa.

Analisis de los datos

str(datos)
## 'data.frame':    5136 obs. of  8 variables:
##  $ YEAR             : int  2025 2025 2025 2025 2025 2025 2025 2025 2025 2025 ...
##  $ MO               : int  1 1 1 1 1 1 1 1 1 1 ...
##  $ DY               : int  1 1 1 1 1 1 1 1 1 1 ...
##  $ HR               : int  0 1 2 3 4 5 6 7 8 9 ...
##  $ ALLSKY_SFC_UVB   : num  0 0 0 0 0 0 0.01 0.14 0.56 1.16 ...
##  $ ALLSKY_SFC_LW_DWN: num  370 372 363 368 367 ...
##  $ PRECTOTCORR      : num  0.48 0.49 0.53 0.48 0.37 0.3 0.27 1.45 1.13 0.85 ...
##  $ PS               : num  84.5 84.5 84.4 84.4 84.4 ...
table(datos$YEAR)
## 
## 2025 
## 5136

Con esta base de datos Analizar la exposición a radiación UVB y las condiciones meteorológicas en Chía para evaluarriesgos para la salud cutánea de la población y derivar recomendaciones de diseño para edificios sostenibles que reduzcan la exposición nociva al sol.

Variables categóricas:

table(datos$YEAR)
## 
## 2025 
## 5136
table(datos$MO)
## 
##   1   2   3   4   5   6   7   8 
## 744 672 744 720 744 720 744  48
table(datos$DY)
## 
##   1   2   3   4   5   6   7   8   9  10  11  12  13  14  15  16  17  18  19  20 
## 192 192 168 168 168 168 168 168 168 168 168 168 168 168 168 168 168 168 168 168 
##  21  22  23  24  25  26  27  28  29  30  31 
## 168 168 168 168 168 168 168 168 144 144  96
barplot(table(datos$ALLSKY_SFC_UVB),las=2)

barplot(table(datos$ALLSKY_SFC_LW_DWN),las=2)

barplot(table(datos$PRECTOTCORR),las=2)

barplot(table(datos$PS),las=2)

Datos faltantes

is.na(datos[1:8,])
##    YEAR    MO    DY    HR ALLSKY_SFC_UVB ALLSKY_SFC_LW_DWN PRECTOTCORR    PS
## 1 FALSE FALSE FALSE FALSE          FALSE             FALSE       FALSE FALSE
## 2 FALSE FALSE FALSE FALSE          FALSE             FALSE       FALSE FALSE
## 3 FALSE FALSE FALSE FALSE          FALSE             FALSE       FALSE FALSE
## 4 FALSE FALSE FALSE FALSE          FALSE             FALSE       FALSE FALSE
## 5 FALSE FALSE FALSE FALSE          FALSE             FALSE       FALSE FALSE
## 6 FALSE FALSE FALSE FALSE          FALSE             FALSE       FALSE FALSE
## 7 FALSE FALSE FALSE FALSE          FALSE             FALSE       FALSE FALSE
## 8 FALSE FALSE FALSE FALSE          FALSE             FALSE       FALSE FALSE
suppressWarnings(missmap(datos))

No hay datos faltantes en esta tabla

Al haber datos negativos, siendo algo imposible en términos físicos, vamos a quitar esos valores.

datos_limpios <- datos %>%
  filter(PS >= 0)
summary(datos_limpios$PS)  
##    Min. 1st Qu.  Median    Mean 3rd Qu.    Max. 
##   82.96   84.40   84.54   84.40   84.65   84.93
datos_limpios <- datos %>%
  filter(ALLSKY_SFC_UVB >= 0)
summary(datos_limpios$ALLSKY_SFC_UVB) 
##    Min. 1st Qu.  Median    Mean 3rd Qu.    Max. 
##  0.0000  0.0000  0.0000  0.3831  0.6200  2.2100
datos_limpios <- datos %>%
  filter(ALLSKY_SFC_LW_DWN >= 0)
summary(datos_limpios$ALLSKY_SFC_LW_DWN) 
##    Min. 1st Qu.  Median    Mean 3rd Qu.    Max. 
##   309.0   375.6   387.2   387.6   400.9   436.5
dim(datos_limpios)
## [1] 2856    8

Disminuye la dimensión

Verificamos normalidad:

safe_ks_test <- function(x) {
  if(length(unique(x)) < 2) return(NA)  
  if(sd(x) == 0) return(NA)             
  
  x_scaled <- scale(x)
  suppressWarnings({
    tryCatch({
      ks.test(x_scaled, "pnorm", mean = 0, sd = 1)$p.value
    }, error = function(e) NA)
  })
}
ks_resultados <- sapply(datos_limpios, safe_ks_test)
ks_tabla <- data.frame(
  Variable = names(ks_resultados),
  KS_pvalue = round(ks_resultados, 4),
  Normalidad = ifelse(ks_resultados > 0.05, "Normal", "No normal"),
  row.names = NULL
)
print(ks_tabla)
##            Variable KS_pvalue Normalidad
## 1              YEAR        NA       <NA>
## 2                MO     0.000  No normal
## 3                DY     0.000  No normal
## 4                HR     0.000  No normal
## 5    ALLSKY_SFC_UVB     0.000  No normal
## 6 ALLSKY_SFC_LW_DWN     0.020  No normal
## 7       PRECTOTCORR     0.000  No normal
## 8                PS     0.008  No normal

Identificamos si hay variables problemáticas

variables_problematicas <- names(which(is.na(ks_resultados)))
if(length(variables_problematicas) > 0) {
  cat("\nVariables con algun problema técnico):\n")
  print(variables_problematicas)
}
## 
## Variables con algun problema técnico):
## [1] "YEAR"

Siendo que Año solo lleva un dato constante (2025), no sea relevante en el estudio y dar NO normal. Vemos que ninguno de nuestros datos son normales.

Visualización boxplot para cada variable numérica:

datos_limpios %>%
  pivot_longer(cols = where(is.numeric), names_to = "Variable", values_to = "Valor") %>%
  ggplot(aes(x = Variable, y = Valor)) +
  geom_boxplot(outlier.colour = "red", fill = "lightblue") +
  theme_minimal() +
  coord_flip() +
  labs(title = "Detección visual de outliers", x = "Variable", y = "Valor")

Detectamos e imputamos los datos atípicos

datos_dect <- datos_limpios
outliers_rosner <- list()
for (var in names(datos_dect)) {
  x <- datos_dect[[var]]
  
  # Verificar si la variable es numérica
  if (!is.numeric(x)) {
    cat("\nVariable", var, "no es numérica. Se omite.\n")
    next  # Saltar a la siguiente variable
  }
  
  # Calcular k_max seguro (evitar k=0 o k > n)
  n <- length(x)
  k_max <- min(10, floor(n * 0.1))
  if (k_max < 1) {
    cat("\nVariable", var, "tiene muy pocos datos. Se omite.\n")
    next
  }
  
  
  if (length(unique(x)) == 1) {
    cat("\nVariable", var, "es constante. No hay outliers.\n")
    next
  }
  
  ros <- tryCatch(
    expr = {
      rosnerTest(x, k = k_max)
    },
    error = function(e) {
      cat("\nError en", var, ":", e$message, "\n")
      NULL
    }
  )
  
  if (!is.null(ros)) {
    outliers_rosner[[var]] <- ros
    cat("\n=== Variable:", var, "===\n")
    print(ros)
  }
}
## 
## Variable YEAR es constante. No hay outliers.
## 
## === Variable: MO ===
## 
## Results of Outlier Test
## -------------------------
## 
## Test Method:                     Rosner's Test for Outliers
## 
## Hypothesized Distribution:       Normal
## 
## Data:                            x
## 
## Sample Size:                     2856
## 
## Test Statistics:                 R.1  = 1.348239
##                                  R.2  = 1.348905
##                                  R.3  = 1.349572
##                                  R.4  = 1.350239
##                                  R.5  = 1.350908
##                                  R.6  = 1.351577
##                                  R.7  = 1.352248
##                                  R.8  = 1.352920
##                                  R.9  = 1.353592
##                                  R.10 = 1.354266
## 
## Test Statistic Parameter:        k = 10
## 
## Alternative Hypothesis:          Up to 10 observations are not
##                                  from the same Distribution.
## 
## Type I Error:                    5%
## 
## Number of Outliers Detected:     0
## 
##    i   Mean.i     SD.i Value Obs.Num    R.i+1 lambda.i+1 Outlier
## 1  0 2.487395 1.121911     4    2161 1.348239   4.287968   FALSE
## 2  1 2.486865 1.121751     4    2162 1.348905   4.287888   FALSE
## 3  2 2.486335 1.121589     4    2163 1.349572   4.287809   FALSE
## 4  3 2.485804 1.121428     4    2164 1.350239   4.287729   FALSE
## 5  4 2.485273 1.121266     4    2165 1.350908   4.287649   FALSE
## 6  5 2.484742 1.121103     4    2166 1.351577   4.287570   FALSE
## 7  6 2.484211 1.120940     4    2167 1.352248   4.287490   FALSE
## 8  7 2.483678 1.120777     4    2168 1.352920   4.287410   FALSE
## 9  8 2.483146 1.120614     4    2169 1.353592   4.287330   FALSE
## 10 9 2.482613 1.120450     4    2170 1.354266   4.287250   FALSE
## 
## 
## 
## === Variable: DY ===
## 
## Results of Outlier Test
## -------------------------
## 
## Test Method:                     Rosner's Test for Outliers
## 
## Hypothesized Distribution:       Normal
## 
## Data:                            x
## 
## Sample Size:                     2856
## 
## Test Statistics:                 R.1  = 1.806546
##                                  R.2  = 1.807896
##                                  R.3  = 1.809249
##                                  R.4  = 1.810605
##                                  R.5  = 1.811965
##                                  R.6  = 1.813327
##                                  R.7  = 1.814693
##                                  R.8  = 1.816061
##                                  R.9  = 1.817433
##                                  R.10 = 1.818808
## 
## Test Statistic Parameter:        k = 10
## 
## Alternative Hypothesis:          Up to 10 observations are not
##                                  from the same Distribution.
## 
## Type I Error:                    5%
## 
## Number of Outliers Detected:     0
## 
##    i   Mean.i     SD.i Value Obs.Num    R.i+1 lambda.i+1 Outlier
## 1  0 15.40336 8.633404    31     721 1.806546   4.287968   FALSE
## 2  1 15.39790 8.629978    31     722 1.807896   4.287888   FALSE
## 3  2 15.39243 8.626545    31     723 1.809249   4.287809   FALSE
## 4  3 15.38696 8.623104    31     724 1.810605   4.287729   FALSE
## 5  4 15.38149 8.619656    31     725 1.811965   4.287649   FALSE
## 6  5 15.37601 8.616201    31     726 1.813327   4.287570   FALSE
## 7  6 15.37053 8.612738    31     727 1.814693   4.287490   FALSE
## 8  7 15.36504 8.609269    31     728 1.816061   4.287410   FALSE
## 9  8 15.35955 8.605792    31     729 1.817433   4.287330   FALSE
## 10 9 15.35406 8.602307    31     730 1.818808   4.287250   FALSE
## 
## 
## 
## === Variable: HR ===
## 
## Results of Outlier Test
## -------------------------
## 
## Test Method:                     Rosner's Test for Outliers
## 
## Hypothesized Distribution:       Normal
## 
## Data:                            x
## 
## Sample Size:                     2856
## 
## Test Statistics:                 R.1  = 1.661034
##                                  R.2  = 1.662128
##                                  R.3  = 1.663225
##                                  R.4  = 1.664324
##                                  R.5  = 1.665424
##                                  R.6  = 1.666528
##                                  R.7  = 1.667633
##                                  R.8  = 1.668740
##                                  R.9  = 1.669850
##                                  R.10 = 1.670962
## 
## Test Statistic Parameter:        k = 10
## 
## Alternative Hypothesis:          Up to 10 observations are not
##                                  from the same Distribution.
## 
## Type I Error:                    5%
## 
## Number of Outliers Detected:     0
## 
##    i   Mean.i     SD.i Value Obs.Num    R.i+1 lambda.i+1 Outlier
## 1  0 11.50000 6.923399     0       1 1.661034   4.287968   FALSE
## 2  1 11.50403 6.921264     0      25 1.662128   4.287888   FALSE
## 3  2 11.50806 6.919124     0      49 1.663225   4.287809   FALSE
## 4  3 11.51209 6.916980     0      73 1.664324   4.287729   FALSE
## 5  4 11.51613 6.914831     0      97 1.665424   4.287649   FALSE
## 6  5 11.52017 6.912678     0     121 1.666528   4.287570   FALSE
## 7  6 11.52421 6.910520     0     145 1.667633   4.287490   FALSE
## 8  7 11.52826 6.908358     0     169 1.668740   4.287410   FALSE
## 9  8 11.53230 6.906191     0     193 1.669850   4.287330   FALSE
## 10 9 11.53635 6.904020     0     217 1.670962   4.287250   FALSE
## 
## 
## 
## === Variable: ALLSKY_SFC_UVB ===
## 
## Results of Outlier Test
## -------------------------
## 
## Test Method:                     Rosner's Test for Outliers
## 
## Hypothesized Distribution:       Normal
## 
## Data:                            x
## 
## Sample Size:                     2856
## 
## Test Statistics:                 R.1  = 3.117333
##                                  R.2  = 3.106111
##                                  R.3  = 3.060574
##                                  R.4  = 3.049009
##                                  R.5  = 3.054527
##                                  R.6  = 3.025694
##                                  R.7  = 2.996667
##                                  R.8  = 2.967449
##                                  R.9  = 2.972570
##                                  R.10 = 2.873994
## 
## Test Statistic Parameter:        k = 10
## 
## Alternative Hypothesis:          Up to 10 observations are not
##                                  from the same Distribution.
## 
## Type I Error:                    5%
## 
## Number of Outliers Detected:     0
## 
##    i    Mean.i      SD.i Value Obs.Num    R.i+1 lambda.i+1 Outlier
## 1  0 0.3831057 0.5860440  2.21    2460 3.117333   4.287968   FALSE
## 2  1 0.3824658 0.5851479  2.20    2317 3.106111   4.287888   FALSE
## 3  2 0.3818290 0.5842600  2.17    2436 3.060574   4.287809   FALSE
## 4  3 0.3812022 0.5834020  2.16     421 3.049009   4.287729   FALSE
## 5  4 0.3805785 0.5825522  2.16    1956 3.054527   4.287649   FALSE
## 6  5 0.3799544 0.5816999  2.14     420 3.025694   4.287570   FALSE
## 7  6 0.3793368 0.5808665  2.12     396 2.996667   4.287490   FALSE
## 8  7 0.3787259 0.5800518  2.10     397 2.967449   4.287410   FALSE
## 9  8 0.3781215 0.5792557  2.10     444 2.972570   4.287330   FALSE
## 10 9 0.3775167 0.5784574  2.04     348 2.873994   4.287250   FALSE
## 
## 
## 
## === Variable: ALLSKY_SFC_LW_DWN ===
## 
## Results of Outlier Test
## -------------------------
## 
## Test Method:                     Rosner's Test for Outliers
## 
## Hypothesized Distribution:       Normal
## 
## Data:                            x
## 
## Sample Size:                     2856
## 
## Test Statistics:                 R.1  = 4.294229
##                                  R.2  = 3.983582
##                                  R.3  = 3.872947
##                                  R.4  = 3.758889
##                                  R.5  = 3.625438
##                                  R.6  = 3.622852
##                                  R.7  = 3.612468
##                                  R.8  = 3.589756
##                                  R.9  = 3.484462
##                                  R.10 = 3.466326
## 
## Test Statistic Parameter:        k = 10
## 
## Alternative Hypothesis:          Up to 10 observations are not
##                                  from the same Distribution.
## 
## Type I Error:                    5%
## 
## Number of Outliers Detected:     1
## 
##    i   Mean.i     SD.i  Value Obs.Num    R.i+1 lambda.i+1 Outlier
## 1  0 387.6236 18.31380 308.98     512 4.294229   4.287968    TRUE
## 2  1 387.6512 18.25773 314.92     530 3.983582   4.287888   FALSE
## 3  2 387.6767 18.21008 317.15     536 3.872947   4.287809   FALSE
## 4  3 387.7014 18.16531 319.42     464 3.758889   4.287729   FALSE
## 5  4 387.7253 18.12342 322.02     532 3.625438   4.287649   FALSE
## 6  5 387.7484 18.08475 322.23     511 3.622852   4.287570   FALSE
## 7  6 387.7714 18.04621 322.58     533 3.612468   4.287490   FALSE
## 8  7 387.7943 18.00798 323.15     535 3.589756   4.287410   FALSE
## 9  8 387.8169 17.97034 325.20     529 3.484462   4.287330   FALSE
## 10 9 387.8389 17.93511 325.67     416 3.466326   4.287250   FALSE
## 
## 
## 
## === Variable: PRECTOTCORR ===
## 
## Results of Outlier Test
## -------------------------
## 
## Test Method:                     Rosner's Test for Outliers
## 
## Hypothesized Distribution:       Normal
## 
## Data:                            x
## 
## Sample Size:                     2856
## 
## Test Statistics:                 R.1  = 16.27643
##                                  R.2  = 16.64534
##                                  R.3  = 16.62721
##                                  R.4  = 16.80364
##                                  R.5  = 16.17348
##                                  R.6  = 16.61217
##                                  R.7  = 16.35847
##                                  R.8  = 15.61968
##                                  R.9  = 16.28419
##                                  R.10 = 16.80536
## 
## Test Statistic Parameter:        k = 10
## 
## Alternative Hypothesis:          Up to 10 observations are not
##                                  from the same Distribution.
## 
## Type I Error:                    5%
## 
## Number of Outliers Detected:     10
## 
##    i   Mean.i     SD.i  Value Obs.Num    R.i+1 lambda.i+1 Outlier
## 1  0 7.648169 27.50491 455.33    2660 16.27643   4.287968    TRUE
## 2  1 7.491363 26.20185 443.63    2661 16.64534   4.287888    TRUE
## 3  2 7.338546 24.90143 421.38    2659 16.62721   4.287809    TRUE
## 4  3 7.193421 23.66789 404.90    2662 16.80364   4.287729    TRUE
## 5  4 7.053973 22.46925 370.46    2663 16.17348   4.287649    TRUE
## 6  5 6.926506 21.41704 362.71    2658 16.61217   4.287570    TRUE
## 7  6 6.801670 20.35694 339.81    2664 16.35847   4.287490    TRUE
## 8  7 6.684784 19.38038 309.40    2665 15.61968   4.287410    TRUE
## 9  8 6.578494 18.53463 308.40    2670 16.28419   4.287330    TRUE
## 10 9 6.472480 17.65315 303.14    2671 16.80536   4.287250    TRUE
## 
## 
## 
## === Variable: PS ===
## 
## Results of Outlier Test
## -------------------------
## 
## Test Method:                     Rosner's Test for Outliers
## 
## Hypothesized Distribution:       Normal
## 
## Data:                            x
## 
## Sample Size:                     2856
## 
## Test Statistics:                 R.1  = 3.050053
##                                  R.2  = 3.055570
##                                  R.3  = 2.919352
##                                  R.4  = 2.853259
##                                  R.5  = 2.857842
##                                  R.6  = 2.791292
##                                  R.7  = 2.795607
##                                  R.8  = 2.799941
##                                  R.9  = 2.804297
##                                  R.10 = 2.768189
## 
## Test Statistic Parameter:        k = 10
## 
## Alternative Hypothesis:          Up to 10 observations are not
##                                  from the same Distribution.
## 
## Type I Error:                    5%
## 
## Number of Outliers Detected:     0
## 
##    i   Mean.i      SD.i Value Obs.Num    R.i+1 lambda.i+1 Outlier
## 1  0 84.54155 0.1414897 84.11     760 3.050053   4.287968   FALSE
## 2  1 84.54170 0.1412837 84.11     784 3.055570   4.287888   FALSE
## 3  2 84.54185 0.1410770 84.13     759 2.919352   4.287809   FALSE
## 4  3 84.54200 0.1408908 84.14     785 2.853259   4.287729   FALSE
## 5  4 84.54214 0.1407142 84.14    1000 2.857842   4.287649   FALSE
## 6  5 84.54228 0.1405370 84.15     761 2.791292   4.287570   FALSE
## 7  6 84.54242 0.1403694 84.15     783 2.795607   4.287490   FALSE
## 8  7 84.54256 0.1402012 84.15     808 2.799941   4.287410   FALSE
## 9  8 84.54269 0.1400327 84.15    1001 2.804297   4.287330   FALSE
## 10 9 84.54283 0.1398636 84.93    1834 2.768189   4.287250   FALSE
for (var in names(outliers_rosner)) {
  
  if (!is.null(outliers_rosner[[var]]) && 
      "all.stats" %in% names(outliers_rosner[[var]])) {
    
    ros_stats <- outliers_rosner[[var]]$all.stats
    filas_out <- ros_stats$Obs.Num[ros_stats$Outlier]  
    
    
    if (length(filas_out) > 0 && all(filas_out %in% 1:nrow(datos_dect))) {
      datos_dect[filas_out, var] <- NA
    }
  }
}

datos_imput <- datos_dect  #

for (var in names(datos_imput)) {
  if (is.numeric(datos_imput[[var]])) {  #
    na_count <- sum(is.na(datos_imput[[var]]))
    
    if (na_count > 0) {
      mediana_val <- median(datos_imput[[var]], na.rm = TRUE)
      datos_imput[[var]][is.na(datos_imput[[var]])] <- mediana_val
      cat(sprintf("Imputados %d outliers en %s con mediana = %.2f\n", 
                  na_count, var, mediana_val))
    }
  }
}
## Imputados 1 outliers en ALLSKY_SFC_LW_DWN con mediana = 387.23
## Imputados 10 outliers en PRECTOTCORR con mediana = 2.09
cat("\nResumen de NAs después del reemplazo:\n")
## 
## Resumen de NAs después del reemplazo:
print(colSums(is.na(datos_dect)))
##              YEAR                MO                DY                HR 
##                 0                 0                 0                 0 
##    ALLSKY_SFC_UVB ALLSKY_SFC_LW_DWN       PRECTOTCORR                PS 
##                 0                 1                10                 0
cat("\nResumen estadístico después de imputación:\n")
## 
## Resumen estadístico después de imputación:
print(summary(datos_imput))
##       YEAR            MO              DY             HR        ALLSKY_SFC_UVB  
##  Min.   :2025   Min.   :1.000   Min.   : 1.0   Min.   : 0.00   Min.   :0.0000  
##  1st Qu.:2025   1st Qu.:1.000   1st Qu.: 8.0   1st Qu.: 5.75   1st Qu.:0.0000  
##  Median :2025   Median :3.000   Median :15.0   Median :11.50   Median :0.0000  
##  Mean   :2025   Mean   :2.487   Mean   :15.4   Mean   :11.50   Mean   :0.3831  
##  3rd Qu.:2025   3rd Qu.:3.000   3rd Qu.:23.0   3rd Qu.:17.25   3rd Qu.:0.6200  
##  Max.   :2025   Max.   :4.000   Max.   :31.0   Max.   :23.00   Max.   :2.2100  
##  ALLSKY_SFC_LW_DWN  PRECTOTCORR            PS       
##  Min.   :314.9     Min.   :  0.000   Min.   :84.11  
##  1st Qu.:375.6     1st Qu.:  0.450   1st Qu.:84.44  
##  Median :387.2     Median :  2.095   Median :84.54  
##  Mean   :387.7     Mean   :  6.353   Mean   :84.54  
##  3rd Qu.:400.9     3rd Qu.:  6.683   3rd Qu.:84.64  
##  Max.   :436.5     Max.   :293.580   Max.   :84.93
datos_imput %>%
  pivot_longer(cols = everything(), names_to = "Variable", values_to = "Valor") %>%
  ggplot(aes(x = Variable, y = Valor)) +
  geom_boxplot(outlier.colour = "red", fill = "lightblue", alpha = 0.7) +
  stat_summary(fun = median, geom = "point", shape = 18, size = 3, color = "blue") +
  theme_minimal() +
  coord_flip() +
  labs(title = "Distribución después de imputación de outliers",
       subtitle = "Puntos azules = medianas imputadas",
       x = "Variable",
       y = "Valor") +
  theme(plot.title = element_text(face = "bold"))

Ya todo limpio

datos_oficiales <- datos_imput

Con nuestro dataset limpio, empezamos nuestro análisis descriptibo y las visualizaciones de estas relaciones para sacar conclusiones.

summary(datos_oficiales)
##       YEAR            MO              DY             HR        ALLSKY_SFC_UVB  
##  Min.   :2025   Min.   :1.000   Min.   : 1.0   Min.   : 0.00   Min.   :0.0000  
##  1st Qu.:2025   1st Qu.:1.000   1st Qu.: 8.0   1st Qu.: 5.75   1st Qu.:0.0000  
##  Median :2025   Median :3.000   Median :15.0   Median :11.50   Median :0.0000  
##  Mean   :2025   Mean   :2.487   Mean   :15.4   Mean   :11.50   Mean   :0.3831  
##  3rd Qu.:2025   3rd Qu.:3.000   3rd Qu.:23.0   3rd Qu.:17.25   3rd Qu.:0.6200  
##  Max.   :2025   Max.   :4.000   Max.   :31.0   Max.   :23.00   Max.   :2.2100  
##  ALLSKY_SFC_LW_DWN  PRECTOTCORR            PS       
##  Min.   :314.9     Min.   :  0.000   Min.   :84.11  
##  1st Qu.:375.6     1st Qu.:  0.450   1st Qu.:84.44  
##  Median :387.2     Median :  2.095   Median :84.54  
##  Mean   :387.7     Mean   :  6.353   Mean   :84.54  
##  3rd Qu.:400.9     3rd Qu.:  6.683   3rd Qu.:84.64  
##  Max.   :436.5     Max.   :293.580   Max.   :84.93

Análisis y visualización

Boxplot irradiancia UVB por mes

ggplot(datos_oficiales, aes(x = MO, y = ALLSKY_SFC_UVB)) +
  geom_boxplot(fill = "lightblue") +
  labs(title = "Irradiancia UVB por mes", x = "Mes", y = "ALLSKY_SFC_UVB (W/m²)") +
  theme_minimal()
## Warning: Continuous x aesthetic
## ℹ did you forget `aes(group = ...)`?

La altura de las cajas indica la dispersión de la irradiancia UVB. Al no tener una caja visible, da a entender que todos los valores son muy similares, es decir, poca variación).

Gráfico de violín para PS por mes:

ggplot(datos_oficiales, aes(x = PS, y = ALLSKY_SFC_UVB)) +
  geom_point(alpha = 0.3) +
  geom_smooth(method = "loess", color = "blue") +
  labs(title = "Relación entre Presión Superficial y UVB", x = "PS (kPa)", y = "ALLSKY_SFC_UVB (W/m²)") +
  theme_minimal()
## `geom_smooth()` using formula = 'y ~ x'

Mediante esta gráfica los datos muestran que, a medida que la presión superficial aumenta ligeramente de 84.25 a 84.75 kPa, la radiación UVB no sigue un patrón específico pues vemos que primero está en 0.5, luego sube a 1.0, vuelve a 0.5 y cae a 0.0, lo que indicar que la presión superficial no es el único factor que influye en la radiación UVB, pudiendo ser las nubes, el ozono de la atmósfera o hora del día en que fue tomado el dato y que puede afectar la medición.

Y vemos que el valor máximo que tomó la variable UVB es de 1.0 W/m² y ocurre en una presión de 84.50 kPa, lo que nos puede decir que estas radiaciones UVB pueden llegar a ser tan altas en presiones igual de altas, por lo cual nos puede dar indicios de correlación.

Por ello, hacemos una matriz de correlación para verificar e identificar cuánta variables se relacionan entre sí:

ggpairs(datos_oficiales, progress = FALSE)
## Warning in cor(x, y): La desviación estándar es cero
## Warning in cor(x, y): La desviación estándar es cero
## Warning in cor(x, y): La desviación estándar es cero
## Warning in cor(x, y): La desviación estándar es cero
## Warning in cor(x, y): La desviación estándar es cero
## Warning in cor(x, y): La desviación estándar es cero
## Warning in cor(x, y): La desviación estándar es cero

Vemos una correlación entre ALLSKY_SPC_LVB y PRECTOTCORR es negativa pero significativa pues mayor precipitación, menor radiación UVB.

En los rayos UVB y la presión hay correlación negativa moderada porque la presión superficial más alta podría asociarse con menor UVB, como haber cielos despejados con alta presión.

Con las precipitaciones y la presión tiene una correlación negativa fuerte pues a mayor presión se relaciona con menor precipitación como en climas secos o los anticiclones.

Ahora vemos las estadísticas por mes:

resumen_mes <- datos_oficiales %>%
  group_by(MO) %>%
  summarise(
    UVB_mediana = median(ALLSKY_SFC_UVB, na.rm = TRUE),
    UVB_media = mean(ALLSKY_SFC_UVB, na.rm = TRUE),
    PS_media = mean(PS, na.rm = TRUE),
    Precip_mediana = median(PRECTOTCORR, na.rm = TRUE)
  )
print(resumen_mes)
##   MO UVB_mediana UVB_media PS_media Precip_mediana
## 1  1           0 0.3960753 84.56856          0.365
## 2  2           0 0.3535565 84.49644          2.240
## 3  3           0 0.3692204 84.56747          3.200
## 4  4           0 0.4126149 84.52852          4.605

Viendo los resultados de estas estadísticas vemos lo siguiente:

  • En la radiación UVB presenta una mediana = 0 en todos los meses, esto indica que más del 50% de los valores UVB son cero, es decir, periodos sin radiación UVB como las noches o días nublados. También se puede ver que la media de la radiación UVB aumenta en los meses de enero (0.396) a abril (0.413), posiblemente por mayor insolación en primavera.

  • En la presión superficial hay poca variación entre meses, diciendo así que hay un clima estable.

  • En cuanto a las precipitaciones hay un aumento progresivo en los meses de enero, con una medida de 0.365 mm, siendo la medida semejante a la época de sequía. Y en abril con 4.605 mm, siendo ese el tope máximo de precipitaciones registrada en el territorio. Eso da un patrón en el aumento de lluvias en la época de la primavera.

Por ello, la radiación UVB es muy baj pero existen horas y/o días con exposición constante. La presión es estable y las precipitaciones aumentan significativamente de invierno a primavera.