Agua y ciudadanía

Autor/a

Sendas, UV, Inecol

Reporte de metodología estadística

Los datos obtenidos del formulario en línea Google Forms se limpiaron para reducir la alta cardinalidad en las preguntas abiertas; la base de datos se revisó con Ydata Profile Report (Ydata, 2024) para evaluar y corregir la calidad. Las preguntas de tipo Likert se ordenaron y refactorizaron antes de incluirlas en los análisis estadísticos. Las variables con información de localización se vincularon a sus correspondientes capas geoespaciales en R (R Core Team, 2024).

Se realizaron varios análisis estadísticos, partiendo de un análisis exploratorio de datos de las variables más importantes y contestadas. Se realizaron correlaciones de Pearson en variables continuas, y se construyeron modelos lineales para variables como el uso del agua o la calidad del servicio como variables de respuesta de los datos demográficos. Se utilizó la prueba t de Student para comparar las medias de los grupos y ANOVA para evaluar la relación entre las variables de respuesta y las variables predictoras; también se utilizaron pruebas de chi-cuadrado para las variables categóricas y pruebas de log-verosimilitud para las variables binarias. Todos los análisis se realizaron en R (R Core Team, 2024).

Código
library(leaflet)
library(lemon)
library(sensemakr)
library(dplyr)
library(ggplot2)
library(readxl)
library(forcats)
library(stringr)
library(ggsci)
library(sf)
library(tidyr)
library(magrittr)
library(stargazer)
library(knitr)

base = read_excel("../El Agua y la Ciudadanía.xlsx") |> 
  dplyr::select(starts_with("limpio"))  |>
  dplyr::filter(limpio_gasto_agua_num < 1000) 

munis = read_sf("~/geoespacial/muni_2018gw.shp",  
                query = "select * from \"muni_2018gw\" where cve_ent = '30' ")

names(base) = gsub("limpio_", "", names(base))

munisb = names(table(base$municipio)[ table(base$municipio) >= 5])
munis = munis |> filter(NOM_MUN %in% munisb)
base = filter(base, municipio %in% munisb)
encuadre = st_bbox(munis) |> st_as_sfc() |> 
  st_transform("+proj=lcc +lat_0=12 +lon_0=-102 +lat_1=17.5 +lat_2=29.5 +x_0=2500000 +y_0=0 +datum=WGS84 +units=m +no_defs") 
cps = read_sf("~/geoespacial/CP_ver.gpkg") |> st_filter(encuadre) 

# refactorización --------------------------------

niveles = c("Pésimo", "Malo", "Regular", "Bueno", "Excelente")
base = within(base, {
  nivel_estudios = factor(nivel_estudios, 
              levels = c("Sin estudios", "Primaria", "Secundaria", "Preparatoria", "Universidad", "Posgrado"))
  almacenamiento = ifelse(is.na(almacenamiento), "No almacenan", almacenamiento)
  dias_sin_serv = factor(dias_sin_serv,
              levels = c("No falta", "1 a 3", "4 a 6", "7 a 9", "10 a 12", "13 a 15", "Más de 15"))
  percep_calidad_servicio = factor(percep_calidad_servicio,
              levels = niveles)
  percep_costo_saneamiento = factor(percep_costo_saneamiento,
              levels = c("Inaceptable", "Poco", "Regular", "Bueno", "Excelente"))
  visita_cuerpo = factor(visita_cuerpo, ordered = TRUE)
  sexo = factor(genero, ordered = TRUE)
  disponibilidad_agua = factor(disponibilidad_agua, labels = c("No", "Sí"))
  razon_NA_checar = factor(razon_NA_checar)
  obtencion_agua = factor(obtencion_agua)
  almacenamiento = factor(almacenamiento)
  fuente_abasto = factor(fuente_abasto)
  nombre_fuente = gsub("Desconozco", "I don't know", nombre_fuente)
  instancia = factor(instancia)
  contexto = factor(contexto)
  actividad_economica = factor(actividad_economica)
  tipo_casa = factor(tipo_casa)
  negativa_visita = factor(negativa_visita)
 afimartiva_visita = factor(afimartiva_visita)
 visita_cuerpo = factor(visita_cuerpo)
 conocimiento_art_1_y_4 = factor(conocimiento_art_1_y_4)
 conocimiento_iniciativa = factor(conocimiento_iniciativa)
 freq_pago = factor(freq_pago)
 destino_agua_servida = factor(destino_agua_servida)
 separacion_negra_gris = factor(separacion_negra_gris)
 destino_drenaje = factor(destino_drenaje)
 sabe_uso_dinero_tarifa_saneamiento = factor(sabe_uso_dinero_tarifa_saneamiento)
 percepcion_pago = factor(percepcion_pago)
 
  })

Perfil demográfico de los respondientes

Código
poblacion = base |> 
  dplyr::filter(edad < 100 & edad > 10 ) |>
  count(edad, sexo, name = "pop") |>
  mutate(edad_cut = cut(edad, breaks = seq(0,100, by = 10), 
                        labels = paste(seq(0,90, by = 10), " a ", 
                                       seq(0,90, by = 10) +10 ))) 
poblacion |>  
  group_by(edad_cut, sexo) |> 
  summarise(pop = sum(pop)) |>
  mutate(pobmf = ifelse(test = sexo == "Masculino", yes = -pop, no = pop)) |>
  ggplot( aes(x = pobmf, 
              y = edad_cut, fill = sexo))  +
  geom_col() +
  scale_x_symmetric(labels = abs) +
  labs(x = "Población", y = "Edad") +
  scale_fill_d3(name = "Sexo")

Código
# plots vars demográficas --------------------------

demog = c("contexto", "actividad_economica", "nivel_estudios", "municipio", "tipo_casa")
preguntas_demog = c("¿En qué contexto vive?", "¿Es actualmente empleado/a de un trabajo remunerado?", "¿Último nivel de estudios?",
  "¿En qué municipio vive?", "¿En qué tipo de casa habitación vive? ")
names(preguntas_demog) = demog

p_demog = lapply(demog, function(x){  base |>
  ggplot(aes(fct_rev(fct_infreq(fct_lump_n(get(x), n = 10, other_level = "Otro")))  ) ) + 
    geom_bar(fill = "dodgerblue") + coord_flip() + geom_text(stat='count',aes(label=..count..),vjust=-.5) +
  labs(x = "", y = "Frecuencia"#, 
       #title = gsub("_", " ", demog[[x]]) |> stringr::str_to_sentence() 
       ) })
names(p_demog) = demog

src = vector(mode = "character", length = length(demog))

for(i in seq_along(demog)){
textotemp = paste0("p_demog[['",  demog[[i]], "']]")
#    ES MUY IMPORTANTE PONER "output: asis" en el chunk    #
src[[i]] = knitr::knit_expand(
    text = c( 
  paste("### ", preguntas_demog[[ demog[[i]] ]]),
  "\n",
  "\n",
  paste0('Total de respuestas: `r .QuartoInlineRender(table(is.na(base[["', demog[[i]], '"]]))[[1]])`'),
  "\n",
  "```{r}",
  "#| echo: false",
  "#| message: false",
  "#| warning: false",
  "\n",
  textotemp,
  "\n",
  "```"
    ))
}

res <- knitr::knit_child(text = src, quiet = TRUE)
cat(res, sep = '\n')

¿En qué contexto vive?

Total de respuestas: 364

¿Es actualmente empleado/a de un trabajo remunerado?

Total de respuestas: 364

¿Último nivel de estudios?

Total de respuestas: 364

¿En qué municipio vive?

Total de respuestas: 364

¿En qué tipo de casa habitación vive?

Total de respuestas: 364

Disponibilidad y suministro de agua

Código
agua = c("disponibilidad_agua", "razon_NA_checar", "obtencion_agua",
         "almacenamiento", "fuente_abasto", "nombre_fuente", "instancia", "visita_cuerpo", "negativa_visita", "afimartiva_visita")

preguntas_agua = c("¿Hay agua siempre disponible en su casa?", 
                      "¿Por qué no has tenido acceso a agua suficiente cuando la has necesitado?",
                      "Cuando te falta agua suficiente, ¿de dónde la obtienes?",
                      "Si almacenas agua en casa, ¿dónde la guardas?",
                      "¿Cuál es la principal fuente de agua de tu casa?",
                      "¿Cómo se llama la fuente de agua que lo abastece? Ej. Río Huitzilapan",
                      "¿De qué organismo depende el suministro de agua de su hogar? (Ej. Comité local, Comisión municipal del agua, Comisión estatal de Veracruz, ninguno)", 
                      "¿Acostumbra visitar el cuerpo de agua más cercano a su vivienda?", 
                      "Si contestó que no visita el cuerpo de agua más cercano, especifique por qué",
                      "Si contestó que visita el cuerpo de agua más cercano, especifique por qué y la frecuencia de sus visitas")
names(preguntas_agua) = agua

p_agua = lapply(agua, function(x){  base |>
    filter(!is.na(get(x))) |>
    ggplot(
      aes(fct_relevel(
            fct_rev(
                fct_infreq(fct_lump_n(get(x), n = 10, other_level = "Otro"))
                ), 
            "Otro", after = 0L)  ) ) + 
    geom_bar(fill = "dodgerblue") + coord_flip() + geom_text(stat='count',aes(label=..count..),vjust=-.1) +
    labs(x = "", y = "Frecuencia"
         #title = gsub("_|NA_checar", " ", agua_en[[x]]) |> stringr::str_to_sentence() 
         ) })
names(p_agua) = agua

src = vector(mode = "character", length = length(agua))
for(i in seq_along(agua)){
textotemp = paste0("p_agua[['",  agua[[i]], "']]")
#    ES MUY IMPORTANTE PONER "output: asis" en el chunk    #
src[[i]] = knitr::knit_expand(
    text = c( 
  paste("### ", preguntas_agua[[ agua[[i]] ]]),
  "\n",
  "\n",
  paste0('Total de respuestas: `r .QuartoInlineRender(table(is.na(base[["', agua[[i]], '"]]))[[1]])`'),
  "\n",
  "```{r}",
  "#| echo: false",
  "#| message: false",
  "#| warning: false",
  "\n",
  textotemp,
  "\n",
  "```"
    ))
}

#    ES MUY IMPORTANTE PONER "output: asis" en el chunk    #
res <- knitr::knit_child(text = src, quiet = TRUE)
cat(res, sep = '\n')

¿Hay agua siempre disponible en su casa?

Total de respuestas: 364

¿Por qué no has tenido acceso a agua suficiente cuando la has necesitado?

Total de respuestas: 327

Cuando te falta agua suficiente, ¿de dónde la obtienes?

Total de respuestas: 311

Si almacenas agua en casa, ¿dónde la guardas?

Total de respuestas: 364

¿Cuál es la principal fuente de agua de tu casa?

Total de respuestas: 363

¿Cómo se llama la fuente de agua que lo abastece? Ej. Río Huitzilapan

Total de respuestas: 274

¿De qué organismo depende el suministro de agua de su hogar? (Ej. Comité local, Comisión municipal del agua, Comisión estatal de Veracruz, ninguno)

Total de respuestas: 232

¿Acostumbra visitar el cuerpo de agua más cercano a su vivienda?

Total de respuestas: 364

Si contestó que no visita el cuerpo de agua más cercano, especifique por qué

Total de respuestas: 218

Si contestó que visita el cuerpo de agua más cercano, especifique por qué y la frecuencia de sus visitas

Total de respuestas: 129

Acceso al agua, alcantarillado, iniciativas sobre el agua y derecho humano al agua

Código
agua = c( "freq_pago", "destino_agua_servida", "separacion_negra_gris", 
         "destino_drenaje", "sabe_uso_dinero_tarifa_saneamiento", 
         "iniciativas_conocidas",
         "conocimiento_iniciativas_saneamiento",
         "conocimiento_art_1_y_4")

preguntas_agua = c( 
 "¿Con qué frecuencia se factura el agua?",
  "¿A dónde va el agua que usas en tu casa?",
  "¿Sabes si en tu colonia se separan las aguas grises?",
  "¿A dónde va el drenaje de tu colonia?", 
  "¿Sabes a qué se destina el dinero recaudado en la cuota de saneamiento?",
  "¿De qué iniciativas, proyectos y acciones a favor del saneamiento tiene conocimiento (por ejemplo, de vecinos de colonias, barrios y comunidades, organizaciones de la sociedad civil, academia, entidades gubernamentales...)?",
  "¿Conoce alguna iniciativa, proyecto, acción que se esté llevando a cabo a favor del saneamiento?",
  "¿Sabe lo que dicen los artículos 1º y 4º de la Constitución sobre el agua?")

#"percepcion_pago",
#"percep_calidad_servicio",
# "percep_costo_saneamiento",

#"Your opinion on the amount of money you pay for water is:"
#  "Your opinion on the water service quality",
# "Your opinion on the cost of your water treatment fee",
names(preguntas_agua) = agua

p_agua = lapply(agua, function(x){  base |>
    dplyr::filter(!is.na(get(x))) |>
    ggplot(
      aes(fct_relevel(
            fct_rev(
                fct_infreq(fct_lump_n(get(x), n = 10, other_level = "Otro"))
                ), 
            "Otro", after = 0L)  ) ) + 
    geom_bar(fill = "dodgerblue") + coord_flip() + geom_text(stat='count',aes(label=..count..),vjust=-.1) +
    labs(x = "", y = "Frecuencia"
         #title = gsub("_|NA_checar", " ", agua[[x]]) |> stringr::str_to_sentence() 
         ) })
names(p_agua) = agua

src = vector(mode = "character", length = length(agua))
for(i in seq_along(agua)){
textotemp = paste0("p_agua[['",  agua[[i]], "']]")
#    ES MUY IMPORTANTE PONER "output: asis" en el chunk    #
src[[i]] = knitr::knit_expand(
    text = c( 
  paste("### ", preguntas_agua[[ agua[[i]] ]]),
  "\n",
  "\n",
  paste0('Total de respuestas: `r .QuartoInlineRender(table(is.na(base[["', agua[[i]], '"]]))[[1]])`'),
  "\n",
  "```{r}",
  "#| echo: false",
  "#| message: false",
  "#| warning: false",
  "\n",
  textotemp,
  "\n",
  "```"
    ))
}

#    ES MUY IMPORTANTE PONER "output: asis" en el chunk    #
res <- knitr::knit_child(text = src, quiet = TRUE)
cat(res, sep = '\n')

¿Con qué frecuencia se factura el agua?

Total de respuestas: 364

¿A dónde va el agua que usas en tu casa?

Total de respuestas: 364

¿Sabes si en tu colonia se separan las aguas grises?

Total de respuestas: 364

¿A dónde va el drenaje de tu colonia?

Total de respuestas: 288

¿Sabes a qué se destina el dinero recaudado en la cuota de saneamiento?

Total de respuestas: 306

¿De qué iniciativas, proyectos y acciones a favor del saneamiento tiene conocimiento (por ejemplo, de vecinos de colonias, barrios y comunidades, organizaciones de la sociedad civil, academia, entidades gubernamentales…)?

Total de respuestas: 248

¿Conoce alguna iniciativa, proyecto, acción que se esté llevando a cabo a favor del saneamiento?

Total de respuestas: 202

¿Sabe lo que dicen los artículos 1º y 4º de la Constitución sobre el agua?

Total de respuestas: 364

Percepciones de calidad y costos

Código
agua = c("percepcion_pago", "percep_calidad_servicio", "percep_costo_saneamiento")

preguntas_agua = c("Su opinión sobre la cantidad de dinero que paga por el agua es:",
                      "Su opinión sobre la calidad del servicio de agua",
                      "Su opinión sobre el coste de la tasa de tratamiento del agua")

names(preguntas_agua) = agua


p_agua = lapply(agua, function(x){  base |>
    filter(!is.na(get(x))) |>
    ggplot(
      aes(fct_lump_n(get(x), n = 10, other_level = "Otro")) ) + 
    geom_bar(fill = "dodgerblue") + scale_fill_d3() +
    coord_flip() + 
    geom_text(stat='count', aes(label=after_stat(count) ), vjust=-.1, 
                             position = "stack" ) +
    labs(x = "", y = "Frecuencia"
         ) })
names(p_agua) = agua

src = vector(mode = "character", length = length(agua))
for(i in seq_along(agua)){
textotemp = paste0("p_agua[['",  agua[[i]], "']]")
#    ES MUY IMPORTANTE PONER "output: asis" en el chunk    #
src[[i]] = knitr::knit_expand(
    text = c( 
  paste("### ", preguntas_agua[[ agua[[i]] ]]),
  "\n",
  "\n",
  paste0('Total de respuestas: `r .QuartoInlineRender(table(is.na(base[["', agua[[i]], '"]])) |> sum())`'),
  "\n",
  "```{r}",
  "#| echo: false",
  "#| message: false",
  "#| warning: false",
  "\n",
  textotemp,
  "\n",
  "```"
    ))
}

#    ES MUY IMPORTANTE PONER "output: asis" en el chunk    #
res <- knitr::knit_child(text = src, quiet = TRUE)
cat(res, sep = '\n')

Su opinión sobre la cantidad de dinero que paga por el agua es:

Total de respuestas: 364

Su opinión sobre la calidad del servicio de agua

Total de respuestas: 364

Su opinión sobre el coste de la tasa de tratamiento del agua

Total de respuestas: 364

Acarreo de agua en hogares

Total de respuestas: 235

Código
por_mun = base |> 
  count(municipio) 

respondientes = left_join(munis, por_mun, 
          by = c("NOM_MUN" = "municipio" )) |>
  filter(!is.na(n)) |>
  mutate(nom_mun = gsub("Tlalnelhuayocan", "Tlalnel.", NOM_MUN)) |>
  st_transform(4326)

por_cp = base |> count(cp) |> mutate(cp = as.character(cp))

# acarreo ----------------------------------------------

acarreo = tidyr::separate(base, acarreo, sep= "/", into = c("acarrea1", "acarrea2", "acarrea3", "acarrea4")) |>
  dplyr::select(starts_with("acarrea"), municipio) |>
  mutate(across(everything(), ~ trimws(.x))) |>
  mutate(across(starts_with("acarrea"), 
                ~ str_match(.x, "\\d+") |> as.numeric(), .names = "edad_{.col}" ) ) |>
  mutate(across(starts_with("acarrea"), 
                ~ str_match(.x, "Femenino|Masculino") |> as.character(), .names = "sexo_{.col}" ) ) |>
  select(-1, -2, -3, -4) |>
  mutate(idn = row_number()) 

acarreo = lapply(0:3, function(x) acarreo[,c(1,2+x,6+x)] |> set_names(c("municipio", "edad", "sexo")) )

acarreo = do.call(rbind, acarreo)

acarreo$sexo = factor(acarreo$sexo, labels = c("Femenino", "Masculino"))

acarreo |>
  ggplot(aes(edad, fill = sexo)) + geom_histogram() +
  facet_wrap(~municipio) +
  scale_fill_d3(name = "Sexo") +
  labs(title = "Acarreo de agua en hogares", subtitle = "Según sexo de los respondientes",
       x = "Edad", y = "Total de personas")

Código
base |>
  mutate(edad_cut = edad - (edad %% 10)) |>
  mutate(acarrea_si_no = ifelse(grepl("Ma|Fem", acarreo), "Sí", "No")) |>
  count(edad_cut, acarrea_si_no, municipio) |>
  ggplot(aes(edad_cut, n, fill = acarrea_si_no)) + geom_col(position = "fill") +
  scale_fill_d3(name = "Se acarrea agua\n en su hogar") +
  facet_wrap(~municipio) +
  labs(title = "Acarreo de agua en hogares", subtitle = "Según edad de los respondientes",
       x = "Edad", y = "Proporción de hogares")

Código
# por cp -------------

respondientes_cp = left_join(cps, por_cp, by = c("d_cp" = "cp") ) |> 
  filter(!is.na(n))  |> st_transform(4326)

Visualizaciones geoespaciales

Total de respuestas: 364

Preguntas:

  1. En qué municipio vive?
  2. Cuál es su código postal?
  3. Si tienen que desplazarse para conseguir agua, cuáles miembros de su familia son responsables de conseguirla? Especifique género y edad.
  4. Cuál es el nombre de la fuente de agua de donde proviene su suministro? Ejemplo: Río Huitzilapan

Las respuestas vacías se consideraban como que no acarreaban agua o que no conocían el nombre de la fuente de abastecimiento

Código
acarreo_cp = base |>
  mutate(acarrea_si_no = ifelse(grepl("Ma|Fem", acarreo), "Sí", "No")) |>
  count(acarrea_si_no, cp) |>
  mutate(cp = as.character(cp)) |>
  group_by(cp) |> 
  mutate(porciento = round(n/sum(n)*100,2 ) ) |> 
  # esto lo hacemos para no perder cps donde un único respondiente dice no acarrear
  mutate(porciento = ifelse(acarrea_si_no == "No" & porciento == 100, 0, porciento)) |>
  mutate(acarrea_si_no = ifelse(acarrea_si_no == "No" & porciento == 0, "Sí",
                                acarrea_si_no)) |>
  filter(acarrea_si_no == "Sí") |> ungroup() |>
  right_join(cps, by = c("cp" = "d_cp")) |> st_as_sf() |>
  filter(!is.na(n)) |>
  st_transform(4326)

know_source = base |>
  mutate(knows_source = ifelse(!grepl("Desc", nombre_fuente), "Sí", "No")) |>
  mutate(knows_source = ifelse(is.na(nombre_fuente), "No", knows_source)) |>
  count(knows_source, cp) |>
  mutate(cp = as.character(cp)) |>
  group_by(cp) |> 
  mutate(porciento = round(n/sum(n)*100,2 ) ) |> 
  # esto lo hacemos para no perder cps donde un único respondiente dice no saber la fuente
  mutate(porciento = ifelse(knows_source == "No" & porciento == 100, 0,
                                porciento)) |>
  mutate(knows_source = ifelse(knows_source == "No" & porciento == 100, 0,
                                "Sí")) |>
  filter(knows_source == "Sí") |> ungroup() |>
  right_join(cps, by = c("cp" = "d_cp")) |> st_as_sf() |>
  filter(!is.na(n)) |>
  st_transform(4326)

pal_resp = colorNumeric(palette = "viridis", domain = respondientes$n)
pal_resp_cp = colorNumeric(palette = "inferno", domain = respondientes_cp$n, reverse = TRUE)
pal_ac_cp = colorNumeric(palette = "plasma", domain = acarreo_cp$porciento, reverse = TRUE)
pal_knows = colorNumeric(palette = "magma", domain = know_source$porciento, reverse = TRUE)
Código
leaflet() |>    
  addProviderTiles(provider = providers$CartoDB.Positron) |> #
  #addTiles() |> 
  setView(lng = -96.94, lat = 19.48, zoom = 11) |>
  addPolygons(data = respondientes, color = pal_resp(respondientes$n), weight = 1.5,
              group = "Número de respondientes por municipalidad",
              fillOpacity = .6,
              popup =  ~paste("Mun:", NOM_MUN, "<hr>Resp.:",  n)) |>
  addPolygons(data = respondientes_cp,
              color = pal_resp_cp(respondientes_cp$n), weight = 1.5,
              group = "Número de respondientes por código postal",
              fillOpacity = .6,
              popup =  ~paste("Código postal:", d_cp, "<hr>Resp:",  n)) |>
  addPolygons(data = acarreo_cp, color = pal_ac_cp(acarreo_cp$porciento), weight = 1.5,
              group = "% de casas que acarrean agua, por CP",
              fillOpacity = .6,
              popup =  ~paste("CP:", cp, "<hr>Porcentaje:",  porciento, "%")) |>
  addPolygons(data = know_source, color = pal_knows(know_source$porciento), weight = 1.5,
              group = "% de respondientes que reportan conocer la fuente de abastecimiento",
              fillOpacity = .6,
              popup =  ~paste("CP:", cp, "<hr>Porcentaje:",  porciento, "%")) |>
  addLegend(pal = pal_resp, values = respondientes$n, title = "N de resp. por municipalidad",
            group = "Número de respondientes por municipalidad", position = "bottomleft") |>
  addLegend(pal = pal_resp_cp, values = respondientes_cp$n, title = "N de resp. por CP",
            group = "Número de respondientes por código postal", position = "bottomleft") |>
  addLegend(pal = pal_ac_cp, values = acarreo_cp$porciento, title = "% de casas que acarrean agua por CP", 
            group = "% de casas que acarrean agua, por CP", position = "bottomleft") |>
  addLegend(pal = pal_knows, values = know_source$porciento, title = "% resp. que conocen la fuente",
            group = "% de respondientes que reportan conocer la fuente de abastecimiento", position = "bottomright") |>
  addLayersControl(overlayGroups = c("Número de respondientes por municipalidad",
                                     "Número de respondientes por código postal",
                                     "% de casas que acarrean agua, por CP",
                                     "% de respondientes que reportan conocer la fuente de abastecimiento") ,
                   options = layersControlOptions(collapsed = FALSE)) |>
  hideGroup(c("Número de respondientes por código postal",
                                     "% de casas que acarrean agua, por CP",
                                     "% de respondientes que reportan conocer la fuente de abastecimiento"))

Escasez a lo largo del año

Total de respuestas: 364 (a la pregunta “¿En qué mes ha sido insuficiente el servicio de agua en su hogar?” que incluía “Ninguno” como opción)

Código
meses = base[,c("municipio", "contexto", "tipo_casa", "nivel_estudios",
              "mes_sin_servicio")] 
#names(meses) = c("municipio", "context", "housing_type", "study_level", "month_without_service")

meses = meses |>  separate_wider_delim("mes_sin_servicio", 
                       delim = ", ", names = c("m1", "m2", "m3", "m4"),
                       too_few = "align_start", too_many = "drop") 

meses |> 
  mutate(falta_servicio = ifelse(m1 == "Ningún mes", "No ha sido interrumpido", "Sí se ha interrumpido") ) |>
  count(municipio, falta_servicio) |>
  knitr::kable()
municipio falta_servicio n
Banderilla Sí se ha interrumpido 32
Coatepec No ha sido interrumpido 38
Coatepec Sí se ha interrumpido 19
Emiliano Zapata No ha sido interrumpido 2
Emiliano Zapata Sí se ha interrumpido 14
Jilotepec No ha sido interrumpido 1
Jilotepec Sí se ha interrumpido 9
Teocelo Sí se ha interrumpido 5
Tlalnelhuayocan No ha sido interrumpido 6
Tlalnelhuayocan Sí se ha interrumpido 7
Xalapa No ha sido interrumpido 58
Xalapa Sí se ha interrumpido 158
Xico No ha sido interrumpido 9
Xico Sí se ha interrumpido 6
Código
meses |>  
  pivot_longer(cols = matches("\\d")) |>
  filter(!is.na(value)) |>
  mutate(value = factor(value, 
                        levels = c("Enero", "Febrero", "Marzo", "Abril", "Mayo", 
                                          "Junio", "Julio", "Agosto", "Septiembre", "Octubre", 
                                          "Noviembre", "Diciembre", "Ningún mes")) ) |> 
  ggplot(aes(value, fill = nivel_estudios)) +
  geom_bar() +  theme(axis.text.x = element_text(angle = 90)) +
  scale_fill_d3(name = "Nivel de estudios") +
  labs(x = "", y = "Total de respondientes") +
  facet_wrap(~municipio) 

Código
# días sin  agua -------------

base |>
  dplyr::filter(!is.na(dias_sin_serv)) |>
  ggplot(aes(dias_sin_serv, fill = contexto)) + 
  geom_bar() +  theme(axis.text.x = element_text(angle = 90)) +
  labs(x  = "Días sin servicio en el último mes", 
       title = "Days sin servicio", y = "Total de respondientes") +
  facet_wrap(~municipio, scales = "free_y") + scale_fill_d3(name = "Contexto")

Código
# consumo de agua --------------

cor(base$gasto_agua_num, base$habitantes, use = "complete.obs")
[1] 0.1505061
Código
base |>
  ggplot(aes(habitantes, gasto_agua_num)) +
  geom_point() +
  scale_fill_d3() +
  facet_wrap(~municipio, scales = "free_y") +
  labs(x = "Habitantes por hogar", y = "Uso diario de agua, litros")

Código
base_cor = base
base = base[,c("gasto_agua_num", "habitantes", "nivel_estudios", 
        "sexo", "edad", "municipio",
        "percep_calidad_servicio", "dias_sin_serv", "percep_costo_saneamiento",
        "destino_drenaje", "visita_cuerpo", "actividad_economica")]

Modelos lineales, anovas, xi cuadrada y análisis log likelihood

Código
# RECORDAR QUE LOS FACTORES QUE NO PONE SON EL INTERCEPTO  


model.gasto = lm(gasto_agua_num ~ habitantes + nivel_estudios + sexo + edad + municipio, data = base)
stargazer(model.gasto, type = "html")
Dependent variable:
gasto_agua_num
habitantes 13.385***
(3.878)
nivel_estudiosSecundaria -67.155
(95.696)
nivel_estudiosPreparatoria -10.581
(78.636)
nivel_estudiosUniversidad 14.900
(78.339)
nivel_estudiosPosgrado 8.759
(78.936)
sexo.L 17.240**
(8.472)
edad 1.462***
(0.456)
municipioCoatepec -34.676
(24.575)
municipioEmiliano Zapata -7.745
(33.783)
municipioJilotepec 158.161***
(39.877)
municipioTeocelo 26.564
(52.572)
municipioTlalnelhuayocan -16.779
(36.589)
municipioXalapa -38.253*
(21.456)
municipioXico -44.411
(35.090)
Constant 25.361
(82.436)
Observations 362
R2 0.172
Adjusted R2 0.138
Residual Std. Error 108.548 (df = 347)
F Statistic 5.137*** (df = 14; 347)
Note: p<0.1; p<0.05; p<0.01
Código
model.costo = lm(percep_costo_saneamiento ~ percep_calidad_servicio + nivel_estudios + municipio +
                   dias_sin_serv + sexo + nivel_estudios + edad,
                 data = base)
Warning in model.response(mf, "numeric"): using type = "numeric" with a factor
response will be ignored
Warning in Ops.factor(y, z$residuals): '-' no es significativo para factores
Código
stargazer(model.costo, type = "html") 
Dependent variable:
percep_costo_saneamiento
percep_calidad_servicioMalo 0.643
percep_calidad_servicioRegular 1.259
percep_calidad_servicioBueno 1.729
percep_calidad_servicioExcelente 2.658
nivel_estudiosSecundaria -1.001
nivel_estudiosPreparatoria 0.023
nivel_estudiosUniversidad 0.170
nivel_estudiosPosgrado 0.157
municipioCoatepec -0.245
municipioEmiliano Zapata 0.056
municipioJilotepec -0.200
municipioTeocelo -1.126
municipioTlalnelhuayocan -0.090
municipioXalapa -0.061
municipioXico -0.162
dias_sin_serv1 a 3 0.149
dias_sin_serv4 a 6 0.044
dias_sin_serv7 a 9 0.049
dias_sin_serv10 a 12 -0.068
dias_sin_serv13 a 15 0.563
dias_sin_servMás de 15 0.024
sexo.L 0.055
edad -0.006
Constant 1.898
Observations 279
Note: p<0.1; p<0.05; p<0.01
Código
# t student -----------------------

#with(base,
#     t.test(gasto_agua_num[sex == "Masculine"], gasto_agua_num[sex == "Femenine"] ))

# with(base,
#      t.test(gasto_agua_num[grepl("Yes", actividad_economica)], 
#             gasto_agua_num[grepl("No", actividad_economica)] ))
# 
# with(base,
#      t.test(gasto_agua_num[contexto == "Urbano"], 
#             gasto_agua_num[contexto == "Rural"] ))

# anovas ---------------

aov(gasto_agua_num ~ nivel_estudios, data = base) |> summary()
                Df  Sum Sq Mean Sq F value Pr(>F)
nivel_estudios   4   80966   20241   1.494  0.203
Residuals      359 4863012   13546               
Código
boxplot(gasto_agua_num ~ nivel_estudios, data = base, 
        varwidth = TRUE, outline = FALSE, las = 2, xlab = "", 
        ylab = "Gasto de agua diario, litros", cex.axis = 0.7)

Código
aov(gasto_agua_num ~ actividad_economica, data = base) |>  summary()
                     Df  Sum Sq Mean Sq F value Pr(>F)  
actividad_economica   7  227186   32455    2.45 0.0183 *
Residuals           356 4716792   13249                 
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Código
ggplot(base, aes(actividad_economica, gasto_agua_num)) + 
  geom_boxplot() + coord_flip() + labs(x = "", y = "Gasto de agua diario, litros")

Código
aov(gasto_agua_num ~ municipio, data = base) |> summary()
             Df  Sum Sq Mean Sq F value   Pr(>F)    
municipio     7  471478   67354   5.361 7.48e-06 ***
Residuals   356 4472500   12563                     
---
Signif. codes:  0 '***' 0.001 '**' 0.01 '*' 0.05 '.' 0.1 ' ' 1
Código
aov(gasto_agua_num ~ municipio, data = base) |> TukeyHSD()
  Tukey multiple comparisons of means
    95% family-wise confidence level

Fit: aov(formula = gasto_agua_num ~ municipio, data = base)

$municipio
                                       diff         lwr        upr     p adj
Coatepec-Banderilla              -45.503289 -120.994768  29.988189 0.5946196
Emiliano Zapata-Banderilla       -33.312500 -137.953283  71.328283 0.9782460
Jilotepec-Banderilla             131.812500    7.999856 255.625144 0.0277593
Teocelo-Banderilla                28.812500 -135.532393 193.157393 0.9994670
Tlalnelhuayocan-Banderilla       -43.110577 -155.512809  69.291655 0.9400744
Xalapa-Banderilla                -60.133796 -124.868821   4.601228 0.0903887
Xico-Banderilla                  -76.720833 -183.661688  30.220022 0.3618368
Emiliano Zapata-Coatepec          12.190789  -84.498719 108.880298 0.9999413
Jilotepec-Coatepec               177.315789   60.146090 294.485489 0.0001481
Teocelo-Coatepec                  74.315789  -85.084372 233.715951 0.8469152
Tlalnelhuayocan-Coatepec           2.392713 -102.647419 107.432844 1.0000000
Xalapa-Coatepec                  -14.630507  -65.520496  36.259483 0.9879684
Xico-Coatepec                    -31.217544 -130.391704  67.956617 0.9796039
Jilotepec-Emiliano Zapata        165.125000   27.359008 302.890992 0.0071080
Teocelo-Emiliano Zapata           62.125000 -112.972520 237.222520 0.9602900
Tlalnelhuayocan-Emiliano Zapata   -9.798077 -137.407479 117.811325 0.9999980
Xalapa-Emiliano Zapata           -26.821296 -115.368014  61.725422 0.9836570
Xico-Emiliano Zapata             -43.408333 -166.234407  79.417740 0.9611237
Teocelo-Jilotepec               -103.000000 -290.187123  84.187123 0.7017138
Tlalnelhuayocan-Jilotepec       -174.923077 -318.672988 -31.173166 0.0058206
Xalapa-Jilotepec                -191.946296 -302.492208 -81.400385 0.0000058
Xico-Jilotepec                  -208.533333 -348.054377 -69.012289 0.0001909
Tlalnelhuayocan-Teocelo          -71.923077 -251.766647 107.920494 0.9258577
Xalapa-Teocelo                   -88.946296 -243.542776  65.650184 0.6514307
Xico-Teocelo                    -105.533333 -282.015045  70.948379 0.6046062
Xalapa-Tlalnelhuayocan           -17.023219 -114.619784  80.573345 0.9994846
Xico-Tlalnelhuayocan             -33.610256 -163.112428  95.891915 0.9934995
Xico-Xalapa                      -16.587037 -107.840389  74.666315 0.9993242
Código
ggplot(base, aes(municipio, gasto_agua_num)) + 
  geom_boxplot(varwidth = TRUE) + coord_flip() + labs(x = "", y = "Gasto de agua diario, litros")

Código
# normalidad

qqnorm(base$gasto_agua_num)
qqline(base$gasto_agua_num)

Código
shapiro.test(base$gasto_agua_num)

    Shapiro-Wilk normality test

data:  base$gasto_agua_num
W = 0.73243, p-value < 2.2e-16
Código
#  no son normales 

# chi squared ----------
table(base$percep_calidad_servicio, base$municipio) |>
  chisq.test()
Warning in chisq.test(table(base$percep_calidad_servicio, base$municipio)):
Chi-squared approximation may be incorrect

    Pearson's Chi-squared test

data:  table(base$percep_calidad_servicio, base$municipio)
X-squared = 26.789, df = 28, p-value = 0.5298
Código
table(base$percep_calidad_servicio, base$visita_cuerpo) |>
  chisq.test() 
Warning in chisq.test(table(base$percep_calidad_servicio, base$visita_cuerpo)):
Chi-squared approximation may be incorrect

    Pearson's Chi-squared test

data:  table(base$percep_calidad_servicio, base$visita_cuerpo)
X-squared = 12.819, df = 4, p-value = 0.01219
Código
table(base$destino_drenaje, base$sexo) |>
  chisq.test()
Warning in chisq.test(table(base$destino_drenaje, base$sexo)): Chi-squared
approximation may be incorrect

    Pearson's Chi-squared test

data:  table(base$destino_drenaje, base$sexo)
X-squared = 41.438, df = 24, p-value = 0.01491
Código
# logistic regression
modlog = glm(visita_cuerpo ~ edad, data = base, family = binomial) 

#summary(modlog) |> kable()
logLik(modlog)
'log Lik.' -240.0286 (df=2)

Nivel de educación y conocimientos sobre el agua

Total de respuestas: 364 (a la pregunta “¿Conoce los artículos 1º y 4º de la constitución mexicana?”) y 364 (a la pregunta “¿Conoce alguna iniciativa, proyecto, acción que se esté llevando a cabo a favor del saneamiento?”)

Correlacionamos una variable ordinal (nivel de estudios más alto) con variables binarias

  • ¿Conoce los artículos 1º y 4º de la constitución mexicana?:
  • 0.1025241
  • ¿Conoce alguna iniciativa, proyecto, acción que se esté llevando a cabo a favor del saneamiento?
  • 0.0692181

Respuestas a la pregunta abierta final

Pregunta: Escriba si tiene algún comentario:

La siguiente lista presenta un resumen de las cuestiones generales debatidas en la pregunta final abierta.

  1. Problemas de infraestructura y servicios de agua:
  • Falta de red hidráulica en localidades cercanas a acuíferos.
  • Problemas con las mangueras que se dañan con facilidad y provocan el desperdicio de agua.
  1. Contaminación y conservación del agua:
  • Preocupación por la contaminación de ríos y masas de agua.
  • Necesidad de proyectos de sostenibilidad y saneamiento.
  1. Educación y sensibilización medioambiental:
  • Falta de valoración y educación sobre el agua.
  • Necesidad de difundir información y sensibilizar.
  1. Gestión y Transparencia:
  • Críticas a la gestión gubernamental y falta de transparencia.
  • Incertidumbre sobre el uso y destino de los pagos por el agua.
  1. Participación y Acción Comunitaria:
  • Interés en participar activamente en proyectos relacionados con el agua.
  • Necesidad de involucrar a la comunidad en las decisiones relacionadas con el agua.
  1. Sostenibilidad y políticas públicas:
  • Necesidad de implementar acciones sostenibles.
  • Crítica a las acciones gubernamentales ineficaces.
  1. Sistema de agua y saneamiento:
  • Problemas con los servicios de saneamiento y la gestión del agua.
  • Críticas a la tarificación del agua y a los servicios mínimos.
  1. Información y resultados:
  • Interés por conocer los resultados de los estudios y encuestas relacionados con el agua.
  • Necesidad de difundir información sobre proyectos y resultados.

Comentarios generales:

Agradecimiento y apoyo a las iniciativas relacionadas con el agua. Preocupación personal y familiar por la calidad y disponibilidad del agua.

Referencias

R Core Team (2024). R: A Language and Environment for Statistical Computing. R Foundation for Statistical Computing, Vienna, Austria. https://www.R-project.org/.

Ydata (2024). Ydata profiling. https://github.com/ydataai/ydata-profiling