Introducción al Análisis

Este informe presenta un análisis multidimensional del mercado de vivienda en la ciudad de Cali. Utilizando un conjunto de datos que detalla características clave de las propiedades, se aplican técnicas de reducción de dimensionalidad y segmentación para descubrir patrones, identificar los principales impulsores del valor inmobiliario y caracterizar los diferentes submercados de la ciudad, generando un modelo K-means para lograr segmentar el mercado.

Fase 1: Carga y Preparación Inicial

Se cargan las librerías y el conjunto de datos vivienda.

suppressPackageStartupMessages({
  library(paqueteMODELOS)
  library(ggplot2)
  library(dplyr)
  library(FactoMineR)
  library(factoextra)
  library(mice)
  library(viridis)
  library(patchwork)
  library(leaflet)
  library(sf)
  library(cluster)
  library(tidyr)
})

# Carga de datos
data(vivienda)

Fase 2: Análisis Exploratorio y Tratamiento de Outliers

Se identifica la presencia de valores ausentes o atípicos para determinar la estrategia de tratamiento.

vars_cuanti <- c("preciom", "areaconst", "parqueaderos", "banios", "habitaciones")

vivienda %>%
  select(all_of(vars_cuanti)) %>%
  pivot_longer(everything(), names_to = "variable", values_to = "valor") %>%
  ggplot(aes(x = variable, y = valor, fill = variable)) +
  geom_boxplot(show.legend = FALSE) +
  facet_wrap(~variable, scales = "free") +
  labs(title = "Detección de Valores Atípicos en Variables Cuantitativas",
       x = "", y = "Valor") +
  theme_minimal()

Los gráficos Bloxplots muestran la presencia de valores extremos,en las variables preciom y areaconst. Eliminar estas observaciones podría sesgar el ejecicio de entendimiento del mercado, ya que pueden pueden ser datos que correspondan a viviendas de gama alta.Mediante la técnica de capping (limitación) es posible remplazar los valores que superan el percentil 99 por el valor de ese mismo percentil, procurando no eliminar valores reales y limitar perder registros relevantes, puesto que por la naturaleza del dataset, es posible que existan viviendas con precios elevados (Lujo) o viviendas de grandes dimensiones.

vivienda_tratada <- vivienda %>%
  mutate(across(all_of(vars_cuanti), ~ {
    q99 <- quantile(., 0.99, na.rm = TRUE)
    ifelse(. > q99, q99, .)
  }, .names = "{.col}"))

Fase 3: Limpieza e Imputación de Datos

La variable parqueaderos presenta valores faltantes, por lo que se imputarán estos datos mediante la mediana, ya que es una medida de tendencia central robusta que no se ve afectada por los valores extremos.

vivienda_imputada <- vivienda_tratada %>%

  mutate(parqueaderos = ifelse(is.na(parqueaderos), 
                               median(parqueaderos, na.rm = TRUE), 
                               parqueaderos))

vivienda_clean <- vivienda_imputada %>%
  select(-id, -piso) %>%
  na.omit()

Fase 4: Análisis de Componentes Principales (PCA)

vars_pca <- c("preciom", "areaconst", "parqueaderos", "banios", "habitaciones")
vivienda_pca_data <- vivienda_clean %>%
  select(all_of(vars_pca))

vivienda_pca_scaled <- scale(vivienda_pca_data)

res.pca <- prcomp(vivienda_pca_scaled)

Varianza Explicada y Cargas Vectoriales

p_scree <- fviz_eig(res.pca, addlabels = TRUE, barfill = "#21908d", barcolor = "#440154") +
  theme_minimal() + labs(title = "Gráfico de Sedimentación")

p_scree

La tabla de cargas muestra cómo se construyen los nuevos componentes. El PC1 parece ser un índice de “Tamaño y Capacidad” de la vivienda, con altas cargas en areaconst, banios, habitaciones y parqueaderos. El PC2 está dominado por preciom, representando una dimensión de “Valor de Mercado”.

# Tabla de cargas
kable(res.pca$rotation, digits = 3, caption = "Cargas de las Variables en cada Componente Principal")
Cargas de las Variables en cada Componente Principal
PC1 PC2 PC3 PC4 PC5
preciom 0.472 0.378 -0.430 0.012 -0.670
areaconst 0.496 -0.052 -0.186 0.715 0.452
parqueaderos 0.408 0.491 0.759 -0.098 0.076
banios 0.488 -0.167 -0.286 -0.690 0.420
habitaciones 0.355 -0.765 0.350 0.045 -0.405

Calidad de Representación (cos2) y Círculo de Correlaciones

p_cos2 <- fviz_cos2(res.pca, choice = "var", axes = 1:2) +
  theme_minimal() +
  labs(title = "Calidad de Representación (cos2)")

# Círculo de correlaciones
p_circle <- fviz_pca_var(res.pca,
                         col.var = "contrib",
                         gradient.cols = viridis(3, direction = -1),
                         repel = TRUE) +
  labs(title = "Círculo de Correlaciones",
       color = "Contribución") +
  theme_minimal()

p_cos2 + p_circle

El gráfico de cos2 muestra que todas las variables están bien representadas en el plano de los dos primeros componentes. El círculo de correlaciones confirma visualmente que las variables de “tamaño” (areaconst, banios) están muy correlacionadas entre sí y son casi ortogonales a preciom, indicando que son dos conceptos distintos en los datos.

Biplot de Individuos

fviz_pca_ind(res.pca, 
             geom.ind = "point",
             pointshape = 21,
             pointsize = 2,
             fill.ind = vivienda_clean$zona,
             col.ind = "black",
             palette = "viridis",
             addEllipses = TRUE,
             legend.title = "Zona",
             repel = TRUE) +
  labs(title = "Proyección de Viviendas por Zona en el Plano PCA",
       subtitle = "PC1: Tamaño/Capacidad | PC2: Valor de Mercado") +
  theme_minimal()

Fase 5: Análisis de Conglomerados (Clustering)

vivienda_CON <- vivienda_clean %>%
  select(zona, estrato, preciom, areaconst, habitaciones, banios) %>%
  mutate(zona = as.numeric(factor(zona)))
vivienda_CON_esc <- scale(vivienda_CON)

fviz_nbclust(vivienda_CON_esc, kmeans, method = "wss") + 
  labs(subtitle = "Método del Codo (Elbow)")

Se seleccionan 3 clústeres para una segmentación granular.

set.seed(123)
kmeans_model <- kmeans(vivienda_CON_esc, centers = 3, nstart = 25)
vivienda_clustered <- vivienda_clean %>%
  mutate(cluster = as.factor(kmeans_model$cluster))

fviz_cluster(list(data = vivienda_CON_esc, cluster = kmeans_model$cluster),
             palette = "viridis", geom = "point", ellipse.type = "convex",
             ggtheme = theme_minimal(), main = "Visualización de Clústeres (K-Means)")

Histogramas por Clúster

# Variables que queremos comparar
vars_hist <- c("preciom", "areaconst", "habitaciones", "banios")

# Graficar histogramas facetados
library(ggplot2)

vivienda_clustered %>%
  pivot_longer(cols = all_of(vars_hist), names_to = "Variable", values_to = "Valor") %>%
  ggplot(aes(x = Valor, fill = cluster)) +
  geom_histogram(alpha = 0.6, position = "identity", bins = 20) +
  facet_wrap(~Variable, scales = "free") +
  scale_fill_viridis_d(name = "Clúster") +
  labs(title = "Distribución de Variables por Clúster",
       x = "Valor", y = "Frecuencia") +
  theme_minimal()

Clúster 1 (Morado) Viviendas de gama media: Estratos 4-5, área y precio moderados. Clúster 2 (Azul): Viviendas de gama alta Agrupa las propiedades con mayor areaconst, preciom, estrato 6, y mayor número de habitaciones y baños.Clúster 3 (Amarillo): Viviendas económicas: Caracterizadas por bajo estrato, menor área, menos habitaciones/baños y el preciom más bajo.

Fase 6: Análisis de Correspondencia (Zona y Estrato)

p_ca_map <- fviz_ca_biplot(res.ca, 
                           repel = TRUE, 
                           col.row = "#440154", 
                           col.col = "#21908d",
                           geom = c("point", "text")) +
  labs(title = "Análisis de Correspondencia entre Zona y Estrato",
       subtitle = "Relación espacial en el plano factorial") +
  theme_minimal()

p_ca_map

p_ca_row <- fviz_contrib(res.ca, choice = "row", axes = 1, top = nrow(tabla_corresp)) +
  labs(title = "Contribución de Zonas a la Dimensión 1") +
  theme_minimal()

p_ca_col <- fviz_contrib(res.ca, choice = "col", axes = 1, top = ncol(tabla_corresp)) +
  labs(title = "Contribución de Estratos a la Dimensión 1") +
  theme_minimal()

p_ca_row + p_ca_col

El análisis de correspondencia entre Zona y Estrato evidencia una asociación clara entre la ubicación geográfica de las propiedades y su nivel socioeconómico. Las zonas de gama alta (como la Zona Oeste y parte de la Zona Sur) se ubican cercanas en el plano factorial a los estratos 5 y 6, lo que confirma su orientación hacia el segmento de mercado más exclusivo. Por el contrario, las zonas Oriente y parte del Norte muestran proximidad con los estratos 2 y 3, reflejando un perfil predominantemente de vivienda económica o de interés social. La distribución de las categorías sugiere que la estructura espacial del mercado inmobiliario en Cali está fuertemente influenciada por la estratificación socioeconómica, lo que respalda la importancia de considerar la localización como un factor clave en la segmentación y valorización de inmuebles.

Conclusiones del Estudio

Dimensiones Clave: El Análisis de Componentes Principales (PCA) revela dos ejes principales e independientes que estructuran el mercado: una primera dimensión de “Tamaño y Capacidad” de la vivienda (impulsada por el área, los baños y las habitaciones) y una segunda dimensión de “Valor de Mercado” (definida por el precio por metro cuadrado y el estrato).

Segmentación del Mercado: El análisis de conglomerados confirma la existencia de tres segmentos de mercado bien definidos: un clúster de perfil económico (estratos bajos y menor tamaño), un clúster de gama media (estratos 4-5 y características moderadas) y un clúster de gama alta (estrato 6, con las propiedades de mayor área y precio).

Asociación Geográfica y Tipología: El análisis de correspondencia demuestra una fuerte asociación entre la zona y el tipo de vivienda. Las casas son más predominantes en las zonas Sur y Norte, mientras que los apartamentos están más asociados con la Zona Oeste, que a su vez se correlaciona con el segmento de gama alta del mercado.