El análisis de la seguridad ciudadana es un aspecto fundamental puesto que tiene un impacto directo en el bienestar social, la calidad de vida, el desarrollo económico y la estabilidad política de una sociedad.
La seguridad ciudadana es un derecho básico de las personas. Proteger la vida, la integridad física y los bienes de los ciudadanos es esencial para asegurar un entorno en el que puedan desarrollarse plenamente y vivir sin temor. Por lo tanto, es importante buscar la forma de mejorar la seguridad y así fomentar un mayor bienestar, fortaleciendo la confianza en las instiruciones y disminuyendo una de las más grande problemáticas sociales.
El análisis de datos geoespaciales y la minería de datos son fundamentales para extraer conocimiento de grandes volúmenes de información. Herramientas como R y librerías especializadas facilitan el procesamiento y visualización de datos espaciales, permitiendo identificar patrones y tendencias que pueden guiar estrategias para mejorar y diseñar políticas públicas dirigidas a prestar más atención a las áreas más críticas, contribuyendo a mejorar la calidad de vida y un desarrollo integral para la sociedad.
La seguridad ciudadana es un aspecto crítico para el desarrollo social y económico de cualquier región. El análisis de los delitos reportados a nivel departamental permite comprender mejor la distribución de la violencia, identificar las regiones más afectadas y detectar patrones que puedan guiar la implementación de políticas públicas más efectivas. Este estudio utiliza una base de datos que recopila información sobre distintos tipos de delitos reportados, clasificados por categorías, departamentos y años, con el objetivo de explorar el comportamiento de la criminalidad en Colombia.
El estudio busca responder a preguntas clave sobre cuáles son las categorías de delitos más frecuentes, qué departamentos presentan una mayor incidencia, y cómo ha evolucionado la violencia a lo largo de los años. Además, se espera que el uso del clustering proporcione una visión integral y visual de la distribución de los delitos, destacando diferencias y similitudes entre departamentos.
A través de este análisis, se espera aportar una perspectiva cuantitativa y detallada sobre el comportamiento de la criminalidad, sirviendo como base para el diseño de políticas públicas más efectivas. La identificación de patrones comunes y áreas prioritarias permitirá a las autoridades focalizar recursos y estrategias en las zonas más afectadas, contribuyendo a la construcción de una sociedad más segura.
En este análisis se empleará el software R como herramienta principal, aprovechando su capacidad para procesar grandes volúmenes de datos y realizar análisis estadísticos avanzados. En particular, se implementará una metodología de clustering, agrupando los departamentos por año según la similitud en los patrones de criminalidad. Este enfoque permitirá identificar agrupamientos de departamentos con características similares en términos de incidencia y tipos de delitos, facilitando la detección de patrones relevantes.
El objetivo de este análisis es analizar la incidencia y distribución de los delitos en los departamentos de Colombia a lo largo de los años mediante el uso de técnicas de clustering, con el fin de identificar patrones territoriales y temporales que permitan comprender las dinámicas de la criminalidad y apoyar la formulación de políticas públicas efectivas en materia de seguridad.
La metodología CRISP-DM (Cross-Industry Standard Process for Data Mining) es un estándar para la ejecución de proyectos de minería de datos. Esta metodología consta de seis fases que guían el proceso desde la comprensión del negocio hasta el despliegue de los resultados.
Durante una semana, las fases de CRISP-DM pueden desarrollarse así:
En este análisis se han seguido una serie de pasos metodológicos para garantizar un estudio estructurado y replicable de los eventos reportados de delitos en diferentes zonas del país. A continuación, se detallan las etapas clave del proceso:
Se recopilaqron datos de la ocurrencia de delitos a nivel nacional
teniendo en cuenta la división por departamento, los cuales se
encuentran en el archivo df_cluster.xlsx
.
El conjunto de datos proporcionado incluye las siguientes variables:
codigo_dane_depto Identificador para cada departamento según clasificación del DANE.
año Fecha en la que se identificó el reporte de caso.
casos: Cantidad de casos registrados para un año y un departamento específicos.
Este catálogo de datos proporciona una descripción detallada de las variables que se utilizarán en el análisis, facilitando la comprensión y manipulación de la información.
La primera etapa técnica consistió en la carga y limpieza de los
datos. Utilizamos la librería read_xlsx
para cargar el
archivo de extensión .xlsx
.
Verificar la consistencia de los códigos de departamento y las fechas registradas.
Una vez los datos estuvieron cargados y preparados, se realizó un análisis descriptivo inicial para entender las características básicas de los eventos. Se calculó la frecuencia de los diferentes tipos de eventos reportados, permitiendo identificar qué eventos eran más comunes.
Se generaron gráficos utilizando ggplot2
para visualizar
la distribución de los eventos en el tiempo y su prevalencia en la
muestra de datos, además de hace uso de indicadores descriptivos para
comprender el comportamiento de cada departamento. Esta etapa ayudó a
identificar patrones generales antes de pasar al análisis
geoespacial.
Se dividirá la información por años para analizar cómo evolucionan los delitos en el tiempo.
Al aplicar la ténica de clusterización para agrupar departamentos con comportamientos similares, también se realizará una comparación interanual, observando la distribución de los cluster a lo largo del tiempo para identificar patrones de cambio o estabilidad.
Finalmente, se consolidaron los resultados de los análisis describiendo las características de los cluster formados, identificando qué tipos de delitos predominan en cada grupo y cómo estos varían entre departamentos.
Se evaluará si ciertos departamentos muestran incrementos o disminuciones en delitos específicos o si hay una estabilidad en el comportamiento delictivo.
La consolidación de estos resultados facilita la comparación y análisis conjunto de los eventos, proporcionando una visión integral de los problemas de seguridad en el país.
Tras la consolidación de los resultados, se interpretaron los hallazgos clave, identificando las zonas de mayor riesgo y los patrones críticos. Esta información fue utilizada para formular recomendaciones prácticas que ayuden a mitigar los problemas detectados, discutiendo las posibles implicaciones en el contexto de la formulación de políticas públicas y priorización de recursos para mitigar los casos de delitos que más afectan a la comunidad.
La metodología empleada permitió llevar a cabo un análisis detallado y replicable, brindando una base sólida para futuras investigaciones y diseño de estrategias de prevención en la seguridad.
En esta sección se realiza la carga y preparación de los datos
obtenidos, además de las librerías que se van a usar a lo largo del
documento. Los datos se encuentran almacenados en un archivo
.xlsx
y se procesan las fechas de creación de cada evento
para asegurarnos de que están en el formato adecuado para realizar
análisis temporal.
El archivo incluye información clave como los códigos del departaamento, fecha de reporte del evento.
library(readr)
library(readxl) # readxl: Para la carga de datos desde archivos Excel.
library(dplyr) # dplyr: Para la manipulación y transformación de datos.
library(lubridate) # lubridate: Para el manejo y procesamiento de fechas y tiempos.
library(leaflet) # leaflet: Para la creación de mapas interactivos.
library(sf) # sf: Para trabajar con datos geoespaciales.
library(mapview) # mapview: Para la visualización interactiva de mapas.
library(spatstat) # spatstat: Para el análisis de patrones espaciales y análisis de densidad.
library(terra) # terra: Para el manejo de datos raster y análisis espacial.
library(leaflet.extras) # leaflet.extras: Para añadir funciones adicionales a los mapas de leaflet
library(ggplot2) # ggplot2: Para la creación de gráficos y visualizaciones.
library(factoextra)
library(cluster)
library(tidyr)
library(tibble)
Primero, definimos una tabla en R con las equivalencias entre el código del DANE y el nombre del departamento. Lo haremos usando un tibble:
# Diccionario de códigos del DANE
dept_names <- tibble::tibble(
codigo_dane_depto = c("05","08","11","13","15","17","18","19","20","23","25","27","41","44","47","50","52","54","63","66","68","70","73","76","81","85","86","88","91","94","95","97","99"),
nombre_departamento = c("ANTIOQUIA","ATLANTICO","BOGOTA","BOLIVAR","BOYACA","CALDAS","CAQUETA","CAUCA","CESAR","CORDOBA","CUNDINAMARCA","CHOCO","HUILA","LA GUAJIRA","MAGDALENA","META","NARIÑO","NORTE SANTANDER","QUINDIO","RISARALDA","SANTANDER","SUCRE","TOLIMA","VALLE","ARAUCA","CASANARE","PUTUMAYO","SAN ANDRES","AMAZONAS","GUAINIA","GUAVIARE","VAUPES","VICHADA")
)
Después de cargar los datos desde df_cluster2.xlsx
,
realizamos una unión (left_join
) para agregar la columna
nombre_departamento
a datos.
De esta manera,
cada registro tendrá su código y el nombre correspondiente.
# Cargar datos desde el archivo Excel
datos <- read_xlsx("df_cluster2.xlsx")
# Convertir el código a carácter por consistencia
datos$codigo_dane_depto <- as.character(datos$codigo_dane_depto)
# Unir el dataframe original con el de nombres de departamentos
datos <- datos %>%
left_join(dept_names, by = "codigo_dane_depto")
Calculamos el total de casos por departamento para identificar los departamentos con mayor incidencia.
library(kableExtra)
# Calcular el total de casos por departamento
top_departments <- datos %>%
group_by(nombre_departamento) %>%
summarise(total_casos = sum(casos)) %>%
arrange(desc(total_casos)) %>%
top_n(5, total_casos)
# Mostrar los departamentos con mayor incidencia
kable(top_departments)
nombre_departamento | total_casos |
---|---|
ANTIOQUIA | 868316 |
VALLE | 533437 |
CUNDINAMARCA | 401307 |
BOGOTA | 325681 |
SANTANDER | 296907 |
Interpretación:
Los departamentos con mayor incidencia de delitos son:
# Filtrar los datos para los departamentos con mayor incidencia y años antes de 2024
datos %>%
filter(nombre_departamento %in% top_departments$nombre_departamento, año < 2024) %>%
ggplot(aes(x = año, y = casos, color = nombre_departamento, group = nombre_departamento)) +
geom_line(size = 1) +
geom_point(size = 2) +
labs(title = "Evolución Temporal de Casos en los Departamentos con Mayor Incidencia",
x = "Año", y = "Número de Casos", color = "Departamento") +
theme_minimal()
Interpretación:
Antioquia (05) y Valle del Cauca (76) presentan los números más altos de casos a lo largo de los años, mostrando una tendencia fluctuante.
Bogotá D.C. (11) muestra un incremento notable en algunos años, posiblemente debido a factores socioeconómicos o migratorios.
La incidencia en Cundinamarca (25) y Santander (68) también es significativa, pero menor en comparación con Antioquia y Valle del Cauca.
Calculamos estadísticas descriptivas para entender la distribución de los casos.
# Estadísticas descriptivas por departamento
estadisticas <- datos %>%
group_by(nombre_departamento) %>%
summarise(media_casos = mean(casos),
mediana_casos = median(casos),
desviacion_std = sd(casos),
casos_min = min(casos),
casos_max = max(casos))
# Mostrar las estadísticas descriptivas
kable(estadisticas)
nombre_departamento | media_casos | mediana_casos | desviacion_std | casos_min | casos_max |
---|---|---|---|---|---|
AMAZONAS | 1157.2 | 1209.0 | 377.8138 | 425 | 1682 |
ANTIOQUIA | 86831.6 | 88138.0 | 31915.8721 | 26691 | 128679 |
ARAUCA | 2908.8 | 3133.0 | 661.7396 | 1309 | 3499 |
ATLANTICO | 18590.4 | 19914.0 | 4597.2318 | 8626 | 24772 |
BOGOTA | 32568.1 | 27532.5 | 20111.6056 | 10523 | 83301 |
BOLIVAR | 16609.8 | 16915.0 | 4516.9769 | 7388 | 24360 |
BOYACA | 14836.1 | 14145.0 | 3949.4168 | 8375 | 24010 |
CALDAS | 13027.8 | 13067.0 | 3580.8334 | 5027 | 17977 |
CAQUETA | 4846.3 | 4933.0 | 1074.0198 | 2329 | 6237 |
CASANARE | 6102.8 | 6144.5 | 1276.9262 | 3190 | 7781 |
CAUCA | 16024.5 | 16648.5 | 3507.4135 | 7634 | 21243 |
CESAR | 13805.7 | 14182.0 | 3365.0274 | 6155 | 17273 |
CHOCO | 3588.7 | 3827.0 | 810.9577 | 1837 | 4771 |
CORDOBA | 10999.0 | 11199.0 | 2760.4845 | 4159 | 14555 |
CUNDINAMARCA | 40130.7 | 39270.0 | 10050.1179 | 17830 | 54131 |
GUAINIA | 640.9 | 597.0 | 205.5775 | 317 | 944 |
GUAVIARE | 1573.1 | 1503.5 | 431.7768 | 922 | 2625 |
HUILA | 15038.2 | 14765.0 | 4057.0324 | 7506 | 23568 |
LA GUAJIRA | 6775.6 | 7431.5 | 1578.1638 | 3292 | 8329 |
MAGDALENA | 10761.3 | 11440.0 | 2684.4032 | 4678 | 14852 |
META | 14312.8 | 14213.5 | 3420.6334 | 7037 | 20001 |
NARIÑO | 14906.3 | 15262.0 | 3674.1811 | 7135 | 21605 |
NORTE SANTANDER | 14417.4 | 14181.0 | 3857.9889 | 5910 | 20325 |
PUTUMAYO | 4075.1 | 3829.5 | 1083.7405 | 2087 | 6112 |
QUINDIO | 8570.7 | 8783.0 | 2068.3100 | 3590 | 11058 |
RISARALDA | 11926.3 | 12400.5 | 3089.2502 | 4662 | 15702 |
SAN ANDRES | 1467.6 | 1521.0 | 285.4623 | 705 | 1727 |
SANTANDER | 29690.7 | 29010.5 | 7754.7670 | 12806 | 41713 |
SUCRE | 9363.9 | 9759.5 | 2254.1601 | 3852 | 11947 |
TOLIMA | 18306.9 | 18762.5 | 4109.2227 | 8710 | 25419 |
VALLE | 53343.7 | 52646.0 | 19332.3872 | 19040 | 91120 |
VAUPES | 380.3 | 393.5 | 145.3150 | 191 | 670 |
VICHADA | 688.9 | 716.0 | 198.1298 | 330 | 990 |
Interpretación:
Existe una variabilidad considerable en el número de casos entre los departamentos. Departamentos como Antioquia tienen una desviación estándar alta, indicando fluctuaciones significativas en el número de casos a lo largo de los años.
Para realizar el análisis de clustering, necesitamos que cada fila
represente un departamento y cada columna represente el número de casos
en un año específico. Usamos pivot_wider
para transformar
los datos a este formato.
# Asegurar que el código del departamento es de tipo carácter
datos$nombre_departamento <- as.character(datos$nombre_departamento)
# Transformar los datos a formato ancho
datos_wide <- datos %>%
pivot_wider(names_from = año, values_from = casos)
# Mostrar las primeras filas del conjunto de datos transformado
head(datos_wide)
Debido a que los departamentos pueden tener escalas de casos muy diferentes, es importante estandarizar los datos antes de realizar el clustering. Esto asegura que cada variable (año) contribuya por igual al análisis.
Utilizamos tres métodos diferentes para determinar el número óptimo de clusters:
Este método evalúa la suma total de cuadrados dentro de los clusters (inercia) para diferentes valores de k.
# Método del Codo
fviz_nbclust(data_scaled_df, kmeans, method = "wss") +
labs(title = "Determinación del Número Óptimo de Clusters - Método del Codo")+
geom_vline(xintercept = 3, linetype = 2)
Interpretación:
Observamos los gráficos y determinamos
que el número óptimo de clusters es 3.
Procedemos a realizar el clustering con k = 3
.
# Aplicar K-Means con k = 3
set.seed(123)
km_res <- kmeans(data_scaled_df, centers = 3, nstart = 25)
# Añadir los resultados del cluster al conjunto de datos original
datos_wide$cluster <- km_res$cluster
# Mostrar los departamentos y sus clusters asignados
datos_wide %>% select(nombre_departamento, cluster)
##
## 1 2 3
## 4 28 1
Para visualizar cómo se distribuyen los clusters en el mapa de Colombia, unimos los resultados del clustering con los datos geoespaciales de los departamentos.
FALSE Reading layer `Subregiones_-_Provincias_de_Colombia' from data source
FALSE `/Users/mac/Desktop/trabajo/seguridad 2/Subregiones_-_Provincias_de_Colombia/Subregiones_-_Provincias_de_Colombia.shp'
FALSE using driver `ESRI Shapefile'
FALSE Simple feature collection with 141 features and 6 fields
FALSE Geometry type: MULTIPOLYGON
FALSE Dimension: XY
FALSE Bounding box: xmin: -9098768 ymin: -470838.7 xmax: -7441398 ymax: 1504865
FALSE Projected CRS: WGS 84 / Pseudo-Mercator
# Asegurar que el código del departamento es de tipo carácter
departamentos_sf$codigo_dane_depto <- as.character(departamentos_sf$COD_DEPTO)
# Unir los datos de clustering con los datos geoespaciales
departamentos_sf <- departamentos_sf %>%
left_join(datos_wide %>% select(codigo_dane_depto, cluster), by = "codigo_dane_depto")
# Verificar la unión
head(departamentos_sf)
Ahora, creamos un mapa que muestra los clusters por departamento.
# Crear mapa de clusters
ggplot(departamentos_sf) +
geom_sf(aes(fill = factor(cluster))) +
scale_fill_discrete(name = "Cluster") +
theme_minimal() +
labs(title = "Clusters de Departamentos de Colombia según Número de Casos",
subtitle = "Análisis de Clustering K-Means",
caption = "Fuente de datos: df_cluster2.xlsx")
Interpretación:
El mapa permite visualizar cómo se distribuyen geográficamente los clusters, identificando regiones con patrones similares de criminalidad.
Calculamos la media de casos por año para cada cluster para entender las características de cada grupo.
# Añadir información de cluster a los datos originales
data_scaled_df$cluster <- km_res$cluster
data_scaled_df$nombre_departamento <- datos_wide$nombre_departamento
# Calcular la media de casos por año para cada cluster
cluster_summary <- data_scaled_df %>%
group_by(cluster) %>%
summarise(across(where(is.numeric), mean))
# Mostrar el resumen
kable(cluster_summary)
cluster | 2015 | 2016 | 2017 | 2018 | 2019 | 2020 | 2021 | 2022 | 2023 | 2024 |
---|---|---|---|---|---|---|---|---|---|---|
1 | 1.1644737 | 1.1084309 | 1.024468 | 1.0588199 | 1.4294691 | 1.6366819 | 1.4908755 | 1.7352157 | 1.5119722 | 1.4993243 |
2 | -0.3183283 | -0.3146594 | -0.313013 | -0.3158934 | -0.3398895 | -0.3550109 | -0.3430419 | -0.3626286 | -0.3444175 | -0.3381052 |
3 | 4.2552988 | 4.3767389 | 4.666492 | 4.6097356 | 3.7990310 | 3.3935769 | 3.6416712 | 3.2127369 | 3.5958014 | 3.4696480 |
Interpretación:
Cluster 1:
Departamentos con incidencia alta de
casos en todos los años.
Cluster 2:
Departamentos con incidencia
media.
Cluster 3:
Departamento con incidencia muy alta,
posiblemente debido a valores excepcionalmente altos en todos los
años.
Interpretación de los Clusters
Cluster 1:
Incluye departamentos como Bogotá D.C.
(11), Santander (68), Cundinamarca (25), y Valle del Cauca
(76).
Cluster 2:
Incluye la mayoría de los departamentos,
con incidencia media.
Cluster 3:
Incluye Antioquia (05), con incidencia
muy alta en comparación con los demás.
El análisis de clustering nos ha permitido identificar tres grupos de departamentos con comportamientos similares en términos de incidencia de delitos:
Cluster 3 (Alta incidencia):
Antioquia se destaca
por tener un número de casos significativamente mayor que otros
departamentos, ubicándose en un cluster por sí solo.
Cluster 1 (Incidencia alta-media):
Departamentos
como Bogotá D.C., Valle del Cauca, Cundinamarca, y Santander presentan
una alta incidencia de delitos, aunque menor que Antioquia.
Cluster 2 (Incidencia media):
La mayoría de los
departamentos con incidencias moderadas de delitos.
A continuación se muestra cómo llevar a cabo un segundo método de clusterización además del K-Means. En este caso, implementaremos clustering jerárquico utilizando el mismo conjunto de datos ya estandarizados (data_scaled_df). De este modo, se podrán comparar los resultados obtenidos por K-Means con los del clustering jerárquico y tener una perspectiva más completa.
Primero, calculamos la distancia entre las observaciones. Por defecto, dist() calcula la distancia euclidiana.
Utilizaremos el método de Ward.D2, que tiende a formar clusters relativamente compactos y similares en tamaño.
El dendrograma nos permite observar la estructura jerárquica de los clusters.
library(factoextra)
# Visualizar el dendrograma y sugerir k = 3 clusters (mismo número usado en K-Means)
fviz_dend(hc_res, k = 3,
rect = TRUE, # Dibuja un rectángulo alrededor de cada grupo
rect_fill = TRUE, # Rellena el rectángulo
rect_border = "jco", # Estilo de los bordes
main = "Dendrograma del Clustering Jerárquico",
xlab = "Departamentos",
ylab = "Altura")
Interpretación del Dendrograma:
Podemos cortar el dendrograma en 3 grupos, como hicimos con K-Means, para comparar los resultados.
# Cortar el dendrograma en k = 3 clusters
hc_clusters <- cutree(hc_res, k = 3)
# Añadir estos clusters al dataframe original
datos_wide$cluster_hc <- hc_clusters
# Mostrar qué departamentos quedan en cada cluster jerárquico
datos_wide %>% select(nombre_departamento, cluster_hc)
Al igual que con K-Means, podemos analizar las características de cada cluster jerárquico. Por ejemplo, calcular la media de casos por año:
# Añadir la clasificación jerárquica a data_scaled_df para facilitar el análisis
data_scaled_df$cluster_hc <- hc_clusters
# Calcular la media de casos por año para cada cluster jerárquico
cluster_hc_summary <- data_scaled_df %>%
group_by(cluster_hc) %>%
summarise(across(where(is.numeric), mean))
kable(cluster_hc_summary)
cluster_hc | 2015 | 2016 | 2017 | 2018 | 2019 | 2020 | 2021 | 2022 | 2023 | 2024 | cluster |
---|---|---|---|---|---|---|---|---|---|---|---|
1 | 4.2552988 | 4.3767389 | 4.666492 | 4.6097356 | 3.7990310 | 3.3935769 | 3.6416712 | 3.2127369 | 3.5958014 | 3.4696480 | 3 |
2 | -0.3183283 | -0.3146594 | -0.313013 | -0.3158934 | -0.3398895 | -0.3550109 | -0.3430419 | -0.3626286 | -0.3444175 | -0.3381052 | 2 |
3 | 1.1644737 | 1.1084309 | 1.024468 | 1.0588199 | 1.4294691 | 1.6366819 | 1.4908755 | 1.7352157 | 1.5119722 | 1.4993243 | 1 |
Interpretación:
Observa si los clusters jerárquicos difieren significativamente de los formados por K-Means.
Puede que el clustering jerárquico forme grupos más equilibrados o distribuya los departamentos de manera distinta según sus patrones de casos.
Si deseas, también puedes visualizar geográficamente cómo quedan distribuidos los clusters jerárquicos repitiendo un proceso similar al realizado con K-Means:
# Unir datos geoespaciales con cluster_hc
departamentos_sf <- departamentos_sf %>%
left_join(datos_wide %>% select(codigo_dane_depto, cluster_hc), by = "codigo_dane_depto")
head(departamentos_sf)
# Mapa de clusters jerárquicos
ggplot(departamentos_sf) +
geom_sf(aes(fill = factor(cluster_hc))) +
scale_fill_discrete(name = "Cluster (HC)") +
theme_minimal() +
labs(title = "Clusters Jerárquicos de Departamentos según Número de Casos",
subtitle = "Análisis de Clustering Jerárquico (Ward)",
caption = "Fuente de datos: df_cluster2.xlsx")
La aplicación de dos métodos de agrupamiento
K-Means y Clustering Jerárquico (método de Ward)
sobre el
mismo conjunto de datos produjo resultados muy similares, lo cual aporta
un mayor grado de confianza en la solidez de la estructura subyacente de
los datos. Las conclusiones más destacadas son:
Consistencia en los Resultados:
La coincidencia de los clusters formados por K-Means
y
el Clustering Jerárquico
indica que la segmentación de los
departamentos basada en el número de casos reportados a lo largo del
tiempo es robusta y no depende fuertemente del método de clusterización
empleado.
Patrones Claros de Incidencia:
Tanto K-Means
como el Clustering Jerárquico
señalan la existencia de un departamento con una incidencia muy alta
(Antioquia), un conjunto de departamentos con incidencia alta-media
(incluyendo Bogotá D.C., Valle del Cauca, Cundinamarca y Santander), y
un grupo más numeroso de departamentos con incidencia media. Esta
coherencia refuerza la interpretación de los patrones de criminalidad
identificados.
Validez del Análisis:
El hecho de obtener la misma segmentación con dos técnicas diferentes mejora la validez interna del análisis. Esto sugiere que la estructura detectada no es un artefacto del algoritmo, sino una propiedad intrínseca de los datos.
Base Sólida para la Toma de Decisiones:
Al confirmar la estabilidad de la clasificación, las autoridades pueden tener mayor seguridad a la hora de diseñar estrategias diferenciadas según el tipo de cluster. Por ejemplo, enfocarse en recursos de prevención más intensivos en los departamentos con mayor incidencia, y medidas más focalizadas para los grupos con incidencia media.
Perspectivas Futuras:
La similitud de resultados entre ambos métodos invita a experimentar con nuevas variables (socioeconómicas, demográficas o del tipo de delitos) o métodos de clusterización alternativos (como DBSCAN o clustering basado en densidad) para profundizar en el entendimiento de la dinámica delictiva y refinar aún más las recomendaciones de política pública.
En esta sección se realizará un análisis de una serie temporal mensual de casos, se ajusta un modelo SARIMA y realiza predicciones para 2024.
A continuación se cargan los datos, los cuales contienen la cantidad total de reportes de cada mes, desde 2015 hasta 2024 y se crea la serie de tiempo con estos datos.
## Registered S3 method overwritten by 'quantmod':
## method from
## as.zoo.data.frame zoo
##
## Attaching package: 'forecast'
## The following object is masked from 'package:nlme':
##
## getResponse
## Rows: 131 Columns: 2
## ── Column specification ────────────────────────────────────────────────────────
## Delimiter: ","
## chr (1): anio_mes
## dbl (1): total_casos
##
## ℹ Use `spec()` to retrieve the full column specification for this data.
## ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.
library(ggplot2)
# Graficar la serie temporal
autoplot(ts_casos) +
labs(title = "Serie de Tiempo Mensual de Casos (2015-2023)",
x = "Año",
y = "Casos",
caption = "Datos agregados mensualmente") +
theme_minimal()
Interpretación:
La serie muestra fluctuaciones significativas, con picos en varios períodos y una tendencia no completamente clara. Procederemos a verificar la estacionariedad.
# Prueba ADF para estacionariedad
adf_resultado <- adf.test(ts_casos)
# Mostrar resultados
if (adf_resultado$p.value < 0.05) {
cat("La serie es estacionaria (valor p =", adf_resultado$p.value, ").\n")
} else {
cat("La serie NO es estacionaria (valor p =", adf_resultado$p.value, "). Aplicar diferenciación.\n")
}
## La serie NO es estacionaria (valor p = 0.05111544 ). Aplicar diferenciación.
Resultado:
La serie no es estacionaria (valor p cercano a 0.05). Aplicaremos diferenciación para garantizar la estacionariedad.
# Aplicar diferenciación
ts_diff <- diff(ts_casos)
# Graficar la serie diferenciada
autoplot(ts_diff) +
labs(title = "Serie Temporal Diferenciada",
x = "Año", y = "Cambio en Casos",
caption = "Serie diferenciada para estacionariedad") +
theme_minimal()
## Warning in adf.test(ts_diff): p-value smaller than printed p-value
if (adf_resultado_diff$p.value < 0.05) {
cat("La serie diferenciada es estacionaria (valor p =", adf_resultado_diff$p.value, ").\n")
}
## La serie diferenciada es estacionaria (valor p = 0.01 ).
Interpretación:
Después de la diferenciación, la serie se vuelve estacionaria, lo que permite ajustar un modelo ARIMA.
# Ajustar modelo ARIMA automáticamente
modelo_arima <- auto.arima(ts_casos, seasonal = TRUE)
# Resumen del modelo ajustado
summary(modelo_arima)
## Series: ts_casos
## ARIMA(0,1,2)(0,0,2)[12]
##
## Coefficients:
## ma1 ma2 sma1 sma2
## -0.6209 -0.2040 0.2312 0.1957
## s.e. 0.0887 0.0941 0.0997 0.1107
##
## sigma^2 = 8.265e+14: log likelihood = -2416.23
## AIC=4842.47 AICc=4842.95 BIC=4856.8
##
## Training set error measures:
## ME RMSE MAE MPE MAPE MASE ACF1
## Training set 2492602 28194977 21254407 -6.01775 24.42049 0.7646041 -0.02384236
Modelo Ajustado:
Se ajusta un modelo ARIMA con los parámetros identificados
automáticamente por auto.arima
.
##
## Ljung-Box test
##
## data: Residuals from ARIMA(0,1,2)(0,0,2)[12]
## Q* = 20.142, df = 20, p-value = 0.4491
##
## Model df: 4. Total lags used: 24
Interpretación:
Los residuos del modelo no muestran patrones significativos, indicando que el modelo ajusta bien los datos.
# Realizar predicción para 12 meses (2024)
prediccion <- forecast(modelo_arima, h = 12)
# Graficar la predicción
autoplot(prediccion) +
labs(title = "Predicción de Casos para 2024",
x = "Año", y = "Casos",
caption = "Modelo SARIMA basado en datos mensuales de 2015-2023") +
theme_minimal()
Interpretación:
La predicción para 2024 muestra un intervalo de confianza para cada mes, considerando la variabilidad histórica de los datos.
La serie original no era estacionaria, pero se corrigió aplicando una diferenciación.
Se ajustó un modelo ARIMA que captura la estacionalidad y tendencias de la serie temporal.
Las predicciones para 2024 muestran posibles fluctuaciones, útiles para planificación y toma de decisiones.
Metodología y enfoques combinados:
Mediante la aplicación de la metodología CRISP-DM
, se
integraron técnicas de minería de datos, análisis geoespacial y modelado
estadístico. Por un lado, se emplearon métodos de agrupamiento
(K-Means y Clustering Jerárquico)
para segmentar los
departamentos según sus patrones de criminalidad a lo largo de varios
años. Por otro lado, el análisis de la serie temporal mensual
(2015-2023)
, ajustando un modelo ARIMA
con
componentes estacionales, permitió proyectar la incidencia de casos a
futuro (2024)
.
Hallazgos en la distribución espacial y temporal de la criminalidad:
El análisis de clusters distinguió tres grupos principales de departamentos según su incidencia delictiva:
Incidencia extremadamente alta: Departamentos
como Antioquia
, que sobresalen por sus niveles
significativamente elevados.
Incidencia alta a media: Ciudades y departamentos como Bogotá D.C., Valle del Cauca, Cundinamarca y Santander, con incidencia importante, aunque sin llegar a los niveles del primer grupo.
Incidencia media: La mayoría de los departamentos, con niveles moderados y más estables. Estos patrones territoriales proporcionan un mapa claro para focalizar esfuerzos y recursos.
Perspectiva temporal y proyecciones:
El análisis de la serie de tiempo, complementario a la segmentación
espacial, reveló fluctuaciones mensuales y permitió determinar que la
tendencia delictiva no es estacionaria en su forma original, requiriendo
diferenciaciones para estabilizar la serie. Tras ajustar un modelo
ARIMA
, se obtuvieron predicciones para el año
2024.
Estas proyecciones son un insumo valioso para
anticipar cambios, planificar acciones preventivas y evaluar el impacto
potencial de medidas de seguridad a corto plazo.
La consistencia entre distintos métodos de agrupamiento refuerza la robustez de los hallazgos sobre la estructura subyacente de los datos. Asimismo, la incorporación del análisis temporal respalda la capacidad de las estrategias de seguridad para no sólo entender el presente, sino también prever escenarios futuros.
Implicaciones prácticas y futuras líneas de acción: La combinación del análisis geoespacial con la proyección temporal brinda un panorama integral para la toma de decisiones informadas. Las autoridades pueden:
Diseñar políticas diferenciadas según el cluster, orientando más recursos y estrategias a los departamentos con mayor incidencia.
Anticipar patrones delictivos futuros gracias a las proyecciones temporales, optimizando la distribución de personal, equipamiento y acciones preventivas.
Implementar un monitoreo continuo para actualizar los modelos con datos recientes, permitiendo responder con agilidad a nuevas dinámicas criminales.
En síntesis, este análisis integrado (clusters espaciales y series temporales) ofrece una base cuantitativa sólida, dinámica y prospectiva que respalda la formulación de políticas públicas más efectivas, la focalización precisa de recursos y la preparación estratégica frente a la evolución futura de la criminalidad.