Portada

UNIVERSIDAD DE EL SALVADOR

FACULTAD DE CIENCIAS ECONÓMICAS

ESCUELA DE ECONOMÍA

CICLO II-2021

“Laboratorio 2: Análisis de Clúster (Conglomerados)”

Métodos para el Análisis Económico.

Docente:

Carlos Ademir Pérez Alas.

Integrantes:

Argueta Velasco Rocío Azucena. (AV14026)

Henríquez Urias Gerson Stanley. (HU17001)

Sánchez Reyes Paola Rosmery. (SR16050)

Velásquez Gonzáles Jóse Roberto. (VG16027)

Grupo Teorico:

03

Ciudad Universitaria, Jueves 18 de noviembre de 2021.

1. Explique en que consiste el análisis de conglomerados

El análisis de cluster permite organizar conjuntos de datos para una mayor especificación de las caracteristicas que estos posean, de forma que pretende explicar por medio de la agrupación como un conjunto de datos es igual o se diferencia de otros.

Según algunos autores los Análisis de Cluster o Conglomerados:

Se ocupan de explorar conjuntos de datos para evaluar si pueden o no resumirse de manera significativa en términos de un pequeño número de grupos o grupos de objetos o individuos que se parecen a cada uno y que son diferentes en algunos aspectos de los individuos de otros grupos. (Everitt et al. 2011)

Mientras que, según (Jain 2008) define el análisis de conglomerados como:

“una técnica de clasificación estadística para descubrir si los individuos de una población caen en diferentes grupos haciendo comparaciones cuantitativas de múltiples características”

Finalmente, (Kassambara 2017) considera que:

La agrupación en clústeres es uno de los métodos de minería de datos importantes para descubrir conocimientos en datos multidimensionales. El objetivo de la agrupación es identificar patrones o grupos de objetos similares dentro de un conjunto de datos de interés.

2.Cuadro comparativo

Se presentara un cuadro comparativo para los diferentes tipos de análisis de cluster

# Se creará una función para insertar las viñetas dentro de la tabla 
lista <- function(...) {
  paste0("<ul>", sprintf('<li>%s</li>', substitute(...())), '</ul>', collapse = '')
}




library(kableExtra)
Cuadro <- data.frame(
'Analisis de cluster'= c("**Jerárquico:**  
Es un metodo alternativo a la agrupación en clústeres de particiones para agrupar objetos en función de su similitud. A diferencia de la agrupación en clústeres de particiones (no jerarquico), la agrupación jerárquica no requieren pre-especificar el número de clusters que se producirán. ",

"**No jerárquico:**  
Es una serie de métodos de agrupación utilizados para clasificar las observaciones, dentro de un conjunto de datos, en varios grupos en función de su similitud. Los algoritmos requieren un analista para especificar el número de clusters que se generarán."),
                    
'Tecnicas Disponibles'= c(lista('Aglomerativo', 'Divisivo'),
                    lista('K-means','K-Medoids (PAM)','Clustering Large Applications (CLARA)')),
  
'Ventajas' =  c(lista('La posibilidad de obtener representaciones en árboles de las observaciones,como los dendrogramas','La agrupación jerárquica no requieren pre-especificar el número de clusters que se                         producirán.'),
                
                lista('Son una alternativa robusta para dividir un conjunto de datos en grupos de observación.',
                      
                      'La agrupación en clústeres de K-means es un algoritmo muy simple y rápido.'
                      ,'Puede lidiar de manera eficiente con muy grandes conjuntos de datos.')),

'Desventajas' = c(lista('Su requerimiento para seleccionar de manera previa un determinado número de clústeres',
                        
'La complejidad del tiempo para el clustering puede dar lugar a tiempos de cálculo muy largos, en comparación con algoritmos eficientes, como K-Means.',
                        
'Si tenemos un conjunto de datos grande, puede ser difícil determinar el número correcto de clusteres por el dendrograma.'),
                  
              lista('Se requiere que el usuario conozca los datos e indique el número apropiado de clústeres que se producirán.',
                        
'Los resultados finales obtenidos son sensibles a la selección aleatoria inicial de los clusteres',
                        
                        'Es sensible a los valores atípicos.',
                        
'Si reorganiza sus datos, es muy posible que obtenga una solución diferente cada vez que cambie el orden de sus datos.')))

kbl(Cuadro,escape = F,caption = "Resumen de Análisis de Cluster") %>% 
  kable_paper(full_width = T, font_size = "14") %>% 
  row_spec(0,background = "lightblue",bold = T,align="center") %>% 
  row_spec(1:2,align = "justify") %>% 
  column_spec(1,border_right = T, width = "30cm") %>% 
  column_spec(2,border_right = T,width = "5cm") %>% 
  column_spec(3:4,border_right = T,width = "20cm") %>% 
  add_footnote("Fuente : Elaboración propia en base a [@jain2008data; @kassambara2017practical]")
Resumen de Análisis de Cluster
Analisis.de.cluster Tecnicas.Disponibles Ventajas Desventajas
Jerárquico:
Es un metodo alternativo a la agrupación en clústeres de particiones para agrupar objetos en función de su similitud. A diferencia de la agrupación en clústeres de particiones (no jerarquico), la agrupación jerárquica no requieren pre-especificar el número de clusters que se producirán.
  • Aglomerativo
  • Divisivo
  • La posibilidad de obtener representaciones en árboles de las observaciones,como los dendrogramas
  • La agrupación jerárquica no requieren pre-especificar el número de clusters que se producirán.
  • Su requerimiento para seleccionar de manera previa un determinado número de clústeres
  • La complejidad del tiempo para el clustering puede dar lugar a tiempos de cálculo muy largos, en comparación con algoritmos eficientes, como K-Means.
  • Si tenemos un conjunto de datos grande, puede ser difícil determinar el número correcto de clusteres por el dendrograma.
No jerárquico:
Es una serie de métodos de agrupación utilizados para clasificar las observaciones, dentro de un conjunto de datos, en varios grupos en función de su similitud. Los algoritmos requieren un analista para especificar el número de clusters que se generarán.
  • K-means
  • K-Medoids (PAM)
  • Clustering Large Applications (CLARA)
  • Son una alternativa robusta para dividir un conjunto de datos en grupos de observación.
  • La agrupación en clústeres de K-means es un algoritmo muy simple y rápido.
  • Puede lidiar de manera eficiente con muy grandes conjuntos de datos.
  • Se requiere que el usuario conozca los datos e indique el número apropiado de clústeres que se producirán.
  • Los resultados finales obtenidos son sensibles a la selección aleatoria inicial de los clusteres
  • Es sensible a los valores atípicos.
  • Si reorganiza sus datos, es muy posible que obtenga una solución diferente cada vez que cambie el orden de sus datos.
a Fuente : Elaboración propia en base a (Jain 2008; Kassambara 2017)

3. Descripción de técnicas disponibles para el análisis de clúster.

Método Jerárquico

Aglomerativo

Trata a cada objeto como un clúster único, posteriormente los pares de clústeres se fusionan sucesivamente hasta convertirse en un gran clúster que contiene todos los objetos. El resultado es un árbol (representación de los objetos), denominado dendrograma, donde su agrupación funciona “de abajo hacia arriba.” Es decir, cada objeto es inicialmente considerado como un grupo de un solo elemento (hoja) y en cada paso del algoritmo, los dos grupos que son los más similares se combinan en un nuevo grupo más grande (nodos), repitiendose hasta que todos los puntos son miembros de un solo gran clúster (raíz). Esta agrupación aglomerativa es buena para identificar agrupaciones pequeñas.

Por otro lado la inversa de la agrupación aglomerativa es la agrupación divisiva, que también se conoce como DIANA (Divise Analysis) y funciona de manera “de arriba hacia abajo.” Comienza con el root, en el que todos los objetos se incluyen en un solo clúster. En cada paso de la iteración, el grupo más heterogéneo se divide en dos. El proceso se repite hasta que todos los objetos están en su propio grupo. Esta agrupación divisiva es buena para identificar grandes agrupaciones.

Sintaxis Aglomerativo

Se deben seguir los siguientes pasos:

  1. Preparación de los datos que deben ser una matriz numérica con; filas que representan observaciones (individuos) y columnas que representan variables.

  2. Calcular información de (des) similitud entre cada par de objetos en los datos a colocar.

  3. Uso de la función de vinculación para agrupar objetos en un árbol de clúster jerárquico, según la información de distancia generada en el paso 1. Objetos / grupos que están cerca aproximadamente se vinculan entre sí mediante la función de vinculación.

  4. Determinar dónde cortar el árbol jerárquico en grupos. Esto crea un partición de los datos.

Script del método

data("USArrests") # Cargar los datos
df <- scale(USArrests) # Standarizar la data
head(df, nrow = 6) # Mostar primeras 6 filas

# Calcular matriz de disimilitud
# df = datos estandarizados
res.dist <- dist(df, method = "euclidean")

as.matrix(res.dist)[1:6, 1:6] # muestra primeras 6 filas y columas de matiz de distancia

# Visualizar el dendograma
library("factoextra")
fviz_dend(res.hc, cex = 0.5)

# Calcular la distancia
res.coph <- cophenetic(res.hc)
#Correlación entre distancia Cophenetic y distancia original
cor(res.dist, res.coph)

#Ejecutarla función nuevamente usando el método de vinculación promedio
res.hc2 <- hclust(res.dist, method = "average")
cor(res.dist, cophenetic(res.hc2))

# Cortar árbol en 4 grupos
grp <- cutree(res.hc, k = 4)
head(grp, n = 4)

# Número de miembros dento del clúster
table(grp)

# Obtener nombres de los miembros de clúster 1
rownames(df)[grp == 1]

# Cortar en 4 grupos y asiganr color por grupos
fviz_dend(res.hc, k = 4, # Cut in four groups
cex = 0.5, # label size
k_colors = c("#2E9FDF", "#00AFBB", "#E7B800", "#FC4E07"),
color_labels_by_k = TRUE, # color por grupos
rect = TRUE # Agregar rectangulo alrededor de los grupos
)

# Observar el resultado de diagrama de dispersión
fviz_cluster(list(data = df, cluster = grp),
palette = c("#2E9FDF", "#00AFBB", "#E7B800", "#FC4E07"),
ellipse.type = "convex", # elipse de concentración
repel = TRUE, # Avoid label overplotting (slow)
show.clust.cent = FALSE, ggtheme = theme_minimal())

library("cluster")
# Anidación aglomerativa (Hierarchical Clustering)
res.agnes <- agnes(x = USArrests, # matriz de datos
stand = TRUE, # estandarizar los datos
metric = "euclidean", # metrica para matriz de distancia
method = "ward" # Método de vinculación
)

# Agrupación de análisis visual
res.diana <- diana(x = USArrests, # matriz de datos
stand = TRUE, # estandarizar los datos
metric = "euclidean" # metrica para matriz de distancia
)

After running agnes() and diana(), you can use the function fviz_dend()[in   factoextra]
to visualize the output:
fviz_dend(res.agnes, cex = 0.6, k = 4)

Métodos No jerárquicos

K-means Clustering

Es el método no jerárquico y no supervisado de aprendizaje automático para particionar un conjunto de datos dado en un conjunto de k grupos, donde se tiene (k conglomerados), donde k representa el número de grupos predefinidos por el analista. Esto lo que hace es clasificar objetos en varios grupos (clústeres), hasta el punto que los objetos dentro del mismo clúster son tan similares como sea posible (alta similitud dentro de la clase) y los objetos de diferentes grupos son lo más diferentes posible (baja similitud entre clases), lo que significa que ninguna observación puede pertenecer a más de un clúster. En la agrupación de k-medias, cada grupo está representado por su centro (centroide) que corresponde a la media de puntos asignados al clúster.

¿Cuál es la idea básica de K-means?

Consiste en definir agrupaciones de modo que el total minimice la variación intra-conglomerado (conocida como variación total dentro del conglomerado). Dentro de la variedad de algoritmos k-medias disponibles el estándar es el Algoritmo de Hartigan-Wong (1979), que define la variación total dentro del conglomerado como la suma de las distancias al cuadrado las distancias euclidianas entre elementos y el correspondiente centroide:

Sintaxis de K-means Clustering

Se deben seguir los isguientes pasos:

  1. Especifique el número de clústeres (K) que se crearán en la solución final (por el analista).

  2. Seleccione aleatoriamente k objetos del conjunto de datos como centros o medias del conglomerado inicial. Los objetos seleccionados también se conocen como medios de clúster O centroide.

  3. Asigna cada observación a su centroide más cercano, basado en el Euclidiana (distancia entre el objeto y el centroide).

  4. Para cada uno de los k conglomerados, actualice el centroide del conglomerado calculando los nuevos valores medios de todos los puntos de datos del conglomerado. El centroide de un grupo es un vector de longitud p que contiene las medias de todas las variables para las observaciones en el k-ésimo grupo; p es el número de variables.

  5. Minimice iterativamente el total dentro de la suma del cuadrado. Es decir, repita los pasos 3 y 4 hasta que las asignaciones del clúster dejen de cambiar o se alcance el número máximo de iteraciones. De forma predeterminada, el software R usa 10 como valor predeterminado para el número máximo de iteraciones.

Script de la tecnica:

data("USArrests") # cargamos el set de datos
df <- scale(USArrests) # normalización de la data
           
head(df, n = 3) # Ver las primeras 3 filas de la data
library(factoextra)
fviz_nbclust(df, kmeans, method = "wss") +
geom_vline(xintercept = 4, linetype = 2)
          
# Calcular k-means con k = 4
set.seed(123)
km.res <- kmeans(df, 4, nstart = 25)
          
# Imprimir los resultados
print(km.res)

aggregate(USArrests, by=list(cluster=km.res$cluster), mean)
dd <- cbind(USArrests, cluster = km.res$cluster)
head(dd)

# Número de conglomerados para cada una de las observaciones 
km.res$cluster
head(km.res$cluster, 4)

# Tamaño de clúster
km.res$size

# Medias de clúster 
km.res$centers
          
fviz_cluster(km.res, data = df,
palette = c("#2E9FDF", "#00AFBB", "#E7B800", "#FC4E07"),
ellipse.type = "euclid", # Concentration ellipse
star.plot = TRUE, # Add segments from centroids to items
repel = TRUE, # Avoid label overplotting (slow)
ggtheme = theme_minimal()
)

K-Medoids (PAM)

Este algoritmo se basa primero en la búsqueda de k objetos representativos entre las observaciones del conjunto de datos, luego se construyen los grupos asignando cada observación al medio más cercano y cada punto de datos no medoide seleccionado se intercambian y se calcula la función objetivo, la cual corresponde a la suma de las disimilitudes de todos los objetos a su medoide más cercano. Este paso intenta mejorar la calidad de la agrupación mediante el intercambio objetos seleccionados (medoides) y objetos no seleccionados. Si la función objetivo puede reducirse intercambiando un objeto seleccionado con un objeto no seleccionado, entonces se realiza el canje continuando hasta que la función objetivo ya no puede ser disminuida.

¿Cuál es el objetivo?

Es encontrar k objetos representativos que minimicen la suma de diferencias de las observaciones con su objeto representativo más cercano.

Sintaxis de K-Medoids (PAM)

Se deben seguir los siguientes pasos:

  1. Seleccione k objetos para convertirlos en medoides, o en caso de que se proporcionen estos objetos utilícelos como medoides;

  2. Calcule la matriz de disimilitud si no se proporcionó;

  3. Asigne cada objeto a su medoide más cercano;

  4. Para cada búsqueda de clúster, si alguno de los objetos del clúster disminuye el coeficiente de disimilitud promedio; si es así, seleccione la entidad que disminuye este coeficiente más como el medoide para este grupo;

  5. Si al menos un medoide ha cambiado, vaya a (3), de lo contrario finalice el algoritmo.

Como se mencionó anteriormente, el algoritmo PAM funciona con una matriz de disimilitud y para calcular esta matriz, el algoritmo puede utilizar dos métricas:

  1. Las distancias euclidianas, que son la raíz de la suma de cuadrados de las diferencias;

  2. Y la distancia de Manhattan que es la suma de distancias absolutas. Tenga en cuenta que, en la práctica, debería obtener resultados similares la mayor parte del tiempo, utilizando distancia euclidiana o de Manhattan. Si sus datos contienen valores atípicos, distancia de Manhattan debería dar resultados más sólidos, mientras que euclidiana se vería influenciada por inusuales valores.

Script del método

data("USArrests") # cargamos el set de datos
df <- scale(USArrests) # normalización de los datos
head(df, n = 3) # vemos las primeras 3 filas de los datos
library(cluster)
library(factoextra)

# La función R fviz_nbclust () [paquete factoextra] proporciona una solución conveniente para estimar el número optimo de conglomerados
fviz_nbclust(df, pam, method = "silhouette")+ #colocamos objeto y el metodo
theme_classic()
pam.res <- pam(df, 2)
print(pam.res)

# Apartir de la grafica obtenida obtendremos la cantidad sugerida de grupo
pam.res <- pam(df, 2) # en este caso la cantidad es 2
print(pam.res)

dd <- cbind(USArrests, cluster = pam.res$cluster) # agregar las     clasificaciones de punto a los datos originales
head(dd, n = 3)

# Medias de clúster: New Mexico, Nebraska
pam.res$medoids

# Número de clúster
head(pam.res$clustering)

#Visualización de Clúster de PAM
fviz_cluster(pam.res,
palette = c("#00AFBB", "#FC4E07"), # color de paleta
ellipse.type = "t", # elipse de concetración 
repel = TRUE, # evitar la superposición de etiquetas
ggtheme = theme_classic()
)

CLARA - Clustering Large Applications

Es una extensión a los métodos k-medoides para tratar datos que contienen una gran número de objetos (más de varios miles de observaciones) con el fin de reducir tiempo de cómputo y problema de almacenamiento de RAM. CLARA considera una pequeña muestra de los datos con tamaño fijo (tamaño de muestra) y aplica el algoritmo PAM para generar un conjunto óptimo de medoides para la muestra. La calidad de los medoides resultantes. se mide por la disimilitud promedio entre cada objeto en todo el conjunto de datos y el medoide de su clúster, definido como la función de costo. Repite los procesos de muestreo y agrupamiento un número preestablecido de veces para minimizar el sesgo de muestreo. Los resultados finales de la agrupación corresponden a la conjunto de medoides con el mínimo costo.

Sintaxis de Clara-Clustering Large Applications

  1. Divida aleatoriamente los conjuntos de datos en varios subconjuntos con tamaño fijo (tamaño de muestra)

  2. Calcule el algoritmo PAM en cada subconjunto y elija el k correspondiente objetos representativos (medoides), luego asignar cada observación de los datos completos ajustado al medoide más cercano.

  3. Calcule la media (o la suma) de las diferencias de las observaciones a su medoide más cercano. Esto se usa como una medida de la bondad de la agrupación.

  4. Conserve el subconjunto de datos para el que la media (o la suma) es mínima. Un más el análisis se lleva a cabo en la partición final.

Script del método

set.seed(1234)
# Generando 500 objetos, divididos dentro de 2 clusters.
df <- rbind(cbind(rnorm(200,0,8), rnorm(200,0,8)),
cbind(rnorm(300,50,8), rnorm(300,50,8)))

# Especificar nombres de columnas y filas
colnames(df) <- c("x", "y")
rownames(df) <- paste0("S", 1:nrow(df))

# Previsualización de la data
head(df, nrow = 6)

# La función fviz_nbclust () [paquete factoextra] proporciona una  solución
library(cluster)
library(factoextra)
fviz_nbclust(df, clara, method = "silhouette")+ #especificar objeto y método
theme_classic()


# Calcular CLARA
clara.res <- clara(df, 2, samples = 50, pamLike = TRUE)
# Imprimir componentes de clara.res
print(clara.res)

# Para agregar las clasificaciones de puntos a los datos originales
dd <- cbind(df, cluster = clara.res$cluster)
head(dd, n = 4)

# Medoids
clara.res$medoids # para acceder a los resultados devueltos por clara

# Clustering
head(clara.res$clustering, 10)

# Visualizando Clúster de Clara
fviz_cluster(clara.res,
palette = c("#00AFBB", "#FC4E07"), # color de paleta
ellipse.type = "t", # elipse de concentración
geom = "point", pointsize = 1,
ggtheme = theme_classic()
)

Librerías utilizadas en R para el caso del análisis de clúster

  • Para el método jerárquico aglomerativo las 2 funciones principales son:

hclust() del paqute stats agnes() del paquete cluster.

  • Para el método jerárquico divisivo se tiene principalmente: diana() del paquete cluster.

  • Librerias que se utilizan en este análisis:

Factoextra

Es un paquete R que facilita la extracción y visualización de la salida de análisis exploratorios de datos multivariados, que incluyen:

Análisis de componentes principales (PCA), que se utiliza para resumir la información contenida en un dato multivariante continuo (es decir, cuantitativo) al reducir la dimensionalidad de los datos sin perder información importante.

Análisis de Correspondencia (AC), que es una extensión del análisis de componentes principales adecuado para analizar una gran tabla de contingencia formada por dos variables cualitativas (o datos categóricos).

Análisis de Correspondencia Múltiple (MCA), que es una adaptación de CA a una tabla de datos que contiene más de dos variables categóricas.

Análisis Factorial Múltiple (MFA) dedicado a conjuntos de datos donde las variables se organizan en grupos (variables cualitativas y/o cuantitativas).

Análisis Factorial Múltiple Jerárquico (HMFA): Una extensión de MFA en una situación en la que los datos están organizados en una estructura jerárquica.

Análisis Factorial de Datos Mixtos (FAMD), un caso particular del MFA, dedicado a analizar un conjunto de datos que contiene variables tanto cuantitativas como cualitativas.

  • Herramientas para el cálculo del número óptimo de clusters en R

Paquete NbClust: implementa 30 índices para evaluar la estructura de los clusters y ayudar a determinar el número de clusters óptimo.

Paquete factoextra: proporciona la función fviz_nbclust()

Paquete stats: posee la función kmeans(). El método de Elbow calcula como de buenos son los clusters generados de 1 hasta N y se queda con el que mejor relacción ofrezca.

  • Creación de clusters en R

Paquete stats: posee la función kmeans() que proporciona particiones con respecto a la distancia Euclidea.

Paquete cluster: posee la función pam() que proporciona particionas alrededor de los medioides y la función clara() es un contanedora de pam puede trabajar con distancias arbitrarias para conjunto de datos grandes.

4.1. Ejemplos prácticos del libro - Análisis no jerárquico.

Se presentarán los ejemplos correspondientes al análisis de clusters no jerarquicos, contenidos en los capitulos 4,5,6 libro de (Kassambara 2017)

Capitulo 4 - K-means

Se utilizará el set de datos “USArrests” de R base

Cáluclo de K-medias clustering en R

# Carga de datos
data("USArrests")
df<- USArrests
df<- na.omit(df)
df_std<- scale(df)
head(df_std,n=3)
##             Murder   Assault   UrbanPop         Rape
## Alabama 1.24256408 0.7828393 -0.5209066 -0.003416473
## Alaska  0.50786248 1.1068225 -1.2117642  2.484202941
## Arizona 0.07163341 1.4788032  0.9989801  1.042878388
# Estimación del numero de clusters
library(factoextra)
fviz_nbclust(df_std, kmeans, method = "wss") +
geom_vline(xintercept = 4, linetype = 2)

# Calcular k-meedias con k = 4
set.seed(123)
km.res <- kmeans(df_std, 4, nstart = 25)
print(km.res)
## K-means clustering with 4 clusters of sizes 8, 13, 16, 13
## 
## Cluster means:
##       Murder    Assault   UrbanPop        Rape
## 1  1.4118898  0.8743346 -0.8145211  0.01927104
## 2 -0.9615407 -1.1066010 -0.9301069 -0.96676331
## 3 -0.4894375 -0.3826001  0.5758298 -0.26165379
## 4  0.6950701  1.0394414  0.7226370  1.27693964
## 
## Clustering vector:
##        Alabama         Alaska        Arizona       Arkansas     California 
##              1              4              4              1              4 
##       Colorado    Connecticut       Delaware        Florida        Georgia 
##              4              3              3              4              1 
##         Hawaii          Idaho       Illinois        Indiana           Iowa 
##              3              2              4              3              2 
##         Kansas       Kentucky      Louisiana          Maine       Maryland 
##              3              2              1              2              4 
##  Massachusetts       Michigan      Minnesota    Mississippi       Missouri 
##              3              4              2              1              4 
##        Montana       Nebraska         Nevada  New Hampshire     New Jersey 
##              2              2              4              2              3 
##     New Mexico       New York North Carolina   North Dakota           Ohio 
##              4              4              1              2              3 
##       Oklahoma         Oregon   Pennsylvania   Rhode Island South Carolina 
##              3              3              3              3              1 
##   South Dakota      Tennessee          Texas           Utah        Vermont 
##              2              1              4              3              2 
##       Virginia     Washington  West Virginia      Wisconsin        Wyoming 
##              3              3              2              2              3 
## 
## Within cluster sum of squares by cluster:
## [1]  8.316061 11.952463 16.212213 19.922437
##  (between_SS / total_SS =  71.2 %)
## 
## Available components:
## 
## [1] "cluster"      "centers"      "totss"        "withinss"     "tot.withinss"
## [6] "betweenss"    "size"         "iter"         "ifault"
#Calculo de la media de cada variable en clusters con la data original

aggregate(USArrests, by=list(cluster=km.res$cluster), mean)
##   cluster   Murder   Assault UrbanPop     Rape
## 1       1 13.93750 243.62500 53.75000 21.41250
## 2       2  3.60000  78.53846 52.07692 12.17692
## 3       3  5.65625 138.87500 73.87500 18.78125
## 4       4 10.81538 257.38462 76.00000 33.19231
# Clasificaciones de puntos a los datos originales

dd <- cbind(USArrests, cluster = km.res$cluster)
head(dd)
##            Murder Assault UrbanPop Rape cluster
## Alabama      13.2     236       58 21.2       1
## Alaska       10.0     263       48 44.5       4
## Arizona       8.1     294       80 31.0       4
## Arkansas      8.8     190       50 19.5       1
## California    9.0     276       91 40.6       4
## Colorado      7.9     204       78 38.7       4

Acceso a los resultados de la función k-means()

# Número de cluster por cada observación

km.res$cluster
##        Alabama         Alaska        Arizona       Arkansas     California 
##              1              4              4              1              4 
##       Colorado    Connecticut       Delaware        Florida        Georgia 
##              4              3              3              4              1 
##         Hawaii          Idaho       Illinois        Indiana           Iowa 
##              3              2              4              3              2 
##         Kansas       Kentucky      Louisiana          Maine       Maryland 
##              3              2              1              2              4 
##  Massachusetts       Michigan      Minnesota    Mississippi       Missouri 
##              3              4              2              1              4 
##        Montana       Nebraska         Nevada  New Hampshire     New Jersey 
##              2              2              4              2              3 
##     New Mexico       New York North Carolina   North Dakota           Ohio 
##              4              4              1              2              3 
##       Oklahoma         Oregon   Pennsylvania   Rhode Island South Carolina 
##              3              3              3              3              1 
##   South Dakota      Tennessee          Texas           Utah        Vermont 
##              2              1              4              3              2 
##       Virginia     Washington  West Virginia      Wisconsin        Wyoming 
##              3              3              2              2              3
head(km.res$cluster, 4)
##  Alabama   Alaska  Arizona Arkansas 
##        1        4        4        1
# Tamaño de cluster
km.res$size
## [1]  8 13 16 13
# Medias del cluster
km.res$centers
##       Murder    Assault   UrbanPop        Rape
## 1  1.4118898  0.8743346 -0.8145211  0.01927104
## 2 -0.9615407 -1.1066010 -0.9301069 -0.96676331
## 3 -0.4894375 -0.3826001  0.5758298 -0.26165379
## 4  0.6950701  1.0394414  0.7226370  1.27693964

Visualización de los clusters

fviz_cluster(km.res, data = df_std,
palette = c("#2E9FDF", "#00AFBB", "#E7B800", "#FC4E07"),
ellipse.type = "euclid", 
star.plot = TRUE, 
repel = TRUE,
ggtheme = theme_minimal()
)

Capitulo 5 K -Medoids PAM (Partitioning Around Medoids)

Se utilizara la misma data del capitulo 4

5.3 Cálculo de K-medoides en R

Cálculo de K-medoides

# Estimación óptima del número de clusters


library(cluster)
library(factoextra)
fviz_nbclust(df_std, pam, method = "silhouette")+
theme_classic()

# Calculando PAM clustering
pam.res <- pam(df_std, 2)
print(pam.res)
## Medoids:
##            ID     Murder    Assault   UrbanPop       Rape
## New Mexico 31  0.8292944  1.3708088  0.3081225  1.1603196
## Nebraska   27 -0.8008247 -0.8250772 -0.2445636 -0.5052109
## Clustering vector:
##        Alabama         Alaska        Arizona       Arkansas     California 
##              1              1              1              2              1 
##       Colorado    Connecticut       Delaware        Florida        Georgia 
##              1              2              2              1              1 
##         Hawaii          Idaho       Illinois        Indiana           Iowa 
##              2              2              1              2              2 
##         Kansas       Kentucky      Louisiana          Maine       Maryland 
##              2              2              1              2              1 
##  Massachusetts       Michigan      Minnesota    Mississippi       Missouri 
##              2              1              2              1              1 
##        Montana       Nebraska         Nevada  New Hampshire     New Jersey 
##              2              2              1              2              2 
##     New Mexico       New York North Carolina   North Dakota           Ohio 
##              1              1              1              2              2 
##       Oklahoma         Oregon   Pennsylvania   Rhode Island South Carolina 
##              2              2              2              2              1 
##   South Dakota      Tennessee          Texas           Utah        Vermont 
##              2              1              1              2              2 
##       Virginia     Washington  West Virginia      Wisconsin        Wyoming 
##              2              2              2              2              2 
## Objective function:
##    build     swap 
## 1.441358 1.368969 
## 
## Available components:
##  [1] "medoids"    "id.med"     "clustering" "objective"  "isolation" 
##  [6] "clusinfo"   "silinfo"    "diss"       "call"       "data"
# Clasificaciones de puntos a los datos originales

dd <- cbind(USArrests, cluster = pam.res$cluster)
head(dd, n = 3)
##         Murder Assault UrbanPop Rape cluster
## Alabama   13.2     236       58 21.2       1
## Alaska    10.0     263       48 44.5       1
## Arizona    8.1     294       80 31.0       1

Accediendo a los resultados de la función PAM

# Cluster medoids: New Mexico, Nebraska
pam.res$medoids
##                Murder    Assault   UrbanPop       Rape
## New Mexico  0.8292944  1.3708088  0.3081225  1.1603196
## Nebraska   -0.8008247 -0.8250772 -0.2445636 -0.5052109
# Números de cluster
head(pam.res$clustering)
##    Alabama     Alaska    Arizona   Arkansas California   Colorado 
##          1          1          1          2          1          1

Visualización de clusters de PAM

fviz_cluster(pam.res,
palette = c("#00AFBB", "#FC4E07"), 
ellipse.type = "t", 
repel = TRUE, 
ggtheme = theme_classic()
)

Capitulo 6 CLARA - Clustering Large Applications

Se utilizara el mismo set de datos USArrests

6.3 Cálculo de CLARA en R

Formato y preparación de datos

set.seed(1234)
# Generación de 500 objetos, divididos dentro de 2 clusters.

df <- rbind(cbind(rnorm(200,0,8), rnorm(200,0,8)),
cbind(rnorm(300,50,8), rnorm(300,50,8)))

# Especificación del nombre de filas y columnas 
colnames(df) <- c("x", "y")

rownames(df) <- paste0("S", 1:nrow(df))
# Previewing the data

head(df, nrow = 6)
##             x        y
## S1  -9.656526 3.881815
## S2   2.219434 5.574150
## S3   8.675529 1.484111
## S4 -18.765582 5.605868
## S5   3.432998 2.493448
## S6   4.048447 6.083699

Estimación óptima del numero de clusters utilizando la función clara ()

library(cluster)
library(factoextra)
fviz_nbclust(df, clara, method = "silhouette")+
theme_classic()

A partir de la gráfica, la cantidad sugerida de grupos es 2.

Cálculo CLARA

clara.res <- clara(df, 2, samples = 50, pamLike = TRUE)

print(clara.res)
## Call:     clara(x = df, k = 2, samples = 50, pamLike = TRUE) 
## Medoids:
##              x         y
## S121 -1.531137  1.145057
## S455 48.357304 50.233499
## Objective function:   9.87862
## Clustering vector:    Named int [1:500] 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 ...
##  - attr(*, "names")= chr [1:500] "S1" "S2" "S3" "S4" "S5" "S6" "S7" ...
## Cluster sizes:            200 300 
## Best sample:
##  [1] S37  S49  S54  S63  S68  S71  S76  S80  S82  S101 S103 S108 S109 S118 S121
## [16] S128 S132 S138 S144 S162 S203 S210 S216 S231 S234 S249 S260 S261 S286 S299
## [31] S304 S305 S312 S315 S322 S350 S403 S450 S454 S455 S456 S465 S488 S497
## 
## Available components:
##  [1] "sample"     "medoids"    "i.med"      "clustering" "objective" 
##  [6] "clusinfo"   "diss"       "call"       "silinfo"    "data"
# Clasiicación de puntos con la data original

dd <- cbind(df, cluster = clara.res$cluster)
head(dd, n = 4)
##             x        y cluster
## S1  -9.656526 3.881815       1
## S2   2.219434 5.574150       1
## S3   8.675529 1.484111       1
## S4 -18.765582 5.605868       1
# Acceso a los resultados retornados de Clara()

 # Medoids

clara.res$medoids
##              x         y
## S121 -1.531137  1.145057
## S455 48.357304 50.233499
# Clustering
head(clara.res$clustering, 10)
##  S1  S2  S3  S4  S5  S6  S7  S8  S9 S10 
##   1   1   1   1   1   1   1   1   1   1

Visualización de clusters

fviz_cluster(clara.res,
palette = c("#00AFBB", "#FC4E07"), 
ellipse.type = "t", 
geom = "point", pointsize = 1,
ggtheme = theme_classic()
)

4.2. Ejemplos prácticos del libro - Análisis Jerárquico.

Se presentarán los ejemplos correspondientes al análisis de clusters jerárquicos, contenidos en los capitulos 7,8,9 libro de (Kassambara 2017)

Capitulo 7 - Agrupación aglomerativa

Se utilizará el set de datos “USArrest” de R base

7.1 Medidas de similitud

res.dist <- dist(df_std, method = "euclidean")

as.matrix(res.dist)[1:6, 1:6]
##             Alabama   Alaska  Arizona Arkansas California Colorado
## Alabama    0.000000 2.703754 2.293520 1.289810   3.263110 2.651067
## Alaska     2.703754 0.000000 2.700643 2.826039   3.012541 2.326519
## Arizona    2.293520 2.700643 0.000000 2.717758   1.310484 1.365031
## Arkansas   1.289810 2.826039 2.717758 0.000000   3.763641 2.831051
## California 3.263110 3.012541 1.310484 3.763641   0.000000 1.287619
## Colorado   2.651067 2.326519 1.365031 2.831051   1.287619 0.000000
res.hc <- hclust(d = res.dist, method = "ward.D2")

7.2 Dendrograma de clusters

library("factoextra")
fviz_dend(res.hc, cex = 0.5)

7.3 Verificación de arboles de cluster

# Cálculo de distancia cophentic
res.coph <- cophenetic(res.hc)

# Correlación entre distancia cophentic y la distancia original

cor(res.dist, res.coph)
## [1] 0.6975266
# Método promedio

res.hc2 <- hclust(res.dist, method = "average")
cor(res.dist, cophenetic(res.hc2))
## [1] 0.7180382

7.4 Corte de dendrograma

# Corte de árbol en 4 grupos

grp <- cutree(res.hc, k = 4)
head(grp, n = 4)
##  Alabama   Alaska  Arizona Arkansas 
##        1        2        2        3
# Número de miembros en cada cluster

table(grp)
## grp
##  1  2  3  4 
##  7 12 19 12
# Obtener el nombre de miembros del cluster 1

rownames(df_std)[grp == 1]
## [1] "Alabama"        "Georgia"        "Louisiana"      "Mississippi"   
## [5] "North Carolina" "South Carolina" "Tennessee"

Visualización de clusters

# Corte en 4 grupos y color por grupos
fviz_dend(res.hc, k = 4, 
cex = 0.5, 
k_colors = c("#2E9FDF", "#00AFBB", "#E7B800", "#FC4E07"),
color_labels_by_k = TRUE, 
rect = TRUE 
)

fviz_cluster(list(data = df_std, cluster = grp),
palette = c("#2E9FDF", "#00AFBB", "#E7B800", "#FC4E07"),
ellipse.type = "convex", 
repel = TRUE, 
show.clust.cent = FALSE, ggtheme = theme_minimal())

7.5 Análisis con paquete cluster ()

library("cluster")

# Agglomerative Nesting (Hierarchical Clustering)

res.agnes <- agnes(x = USArrests, 
stand = TRUE, 
metric = "euclidean", 
method = "ward" 
)

# DIvisive ANAlysis Clustering

res.diana <- diana(x = USArrests, 
stand = TRUE, 
metric = "euclidean" 
)

# Visualización de DIANA

fviz_dend(res.agnes, cex = 0.6, k = 4)

Capitulo 8 - Comparación de dendrogramas

8.1 Preparación de la data

library(dendextend)

# Subset de 10 filas

set.seed(123)
ss <- sample(1:50, 10)
df <- df_std[ss,]

8.2 Comparación de dendrogramas

#Calcular la matriz de distancia

res.dist <- dist(df, method = "euclidean")

# Calcular 2 clusters jerárquicos

hc1 <- hclust(res.dist, method = "average")
hc2 <- hclust(res.dist, method = "ward.D2")

# Creación de dos dendrogramas

dend1 <- as.dendrogram (hc1)
dend2 <- as.dendrogram (hc2)

# Creación de lista que contiene los dos dendrogramas

dend_list <- dendlist(dend1, dend2)

Visualización de la comparación de dedrogramas con la función tanglegram

tanglegram(dend1, dend2)

tanglegram(dend1, dend2,
highlight_distinct_edges = FALSE, 
common_subtrees_color_lines = FALSE, 
common_subtrees_color_branches = TRUE, 
main = paste("entanglement =", round(entanglement(dend_list), 2))
)

Correlación de las matrices entre la lista de dendrogramas

# Correlación Cophenetic de la matriz

cor.dendlist(dend_list, method = "cophenetic")
##           [,1]      [,2]
## [1,] 1.0000000 0.9925544
## [2,] 0.9925544 1.0000000
# Correalción Baker de la matriz

cor.dendlist(dend_list, method = "baker")
##           [,1]      [,2]
## [1,] 1.0000000 0.9895528
## [2,] 0.9895528 1.0000000
# Coeficiente de correlación Cophenetic 

cor_cophenetic(dend1, dend2)
## [1] 0.9925544
# Coeficiente de correlación Baker 

cor_bakers_gamma(dend1, dend2)
## [1] 0.9895528

Creación de multiples dendrogramas por encadenamiento

dend1 <- df %>% dist %>% hclust("complete") %>% as.dendrogram
dend2 <- df %>% dist %>% hclust("single") %>% as.dendrogram
dend3 <- df %>% dist %>% hclust("average") %>% as.dendrogram
dend4 <- df %>% dist %>% hclust("centroid") %>% as.dendrogram

# Calculo de matriz de correlación

dend_list <- dendlist("Complete" = dend1, "Single" = dend2,
"Average" = dend3, "Centroid" = dend4)
cors <- cor.dendlist(dend_list)


round(cors, 2)
##          Complete Single Average Centroid
## Complete     1.00   0.46    0.45     0.30
## Single       0.46   1.00    0.23     0.17
## Average      0.45   0.23    1.00     0.31
## Centroid     0.30   0.17    0.31     1.00
# Visualización de la matriz de correlación usando el paquete corrplot

library(corrplot)
corrplot(cors, "pie", "lower")

Capitulo 9 - Visualización de dendrogramas

Visualización de dendrogramas

# Calculo de distancias y clusters jerarquicos

dd <- dist(scale(USArrests), method = "euclidean")
hc <- hclust(dd, method = "ward.D2")

library(factoextra)
fviz_dend(hc, k = 4, # Corte en 4 grupos
cex = 0.5, # tamaño de ejes
k_colors = c("#2E9FDF", "#00AFBB", "#E7B800", "#FC4E07"),
color_labels_by_k = TRUE, # color de ejes por grupo
rect = TRUE, # Agregar un rectangulo alrededor de los grupos
rect_border = c("#2E9FDF", "#00AFBB", "#E7B800", "#FC4E07"),
rect_fill = TRUE)

# Cambio de color con jco

fviz_dend(hc, k = 4, cex = 0.4, horiz = TRUE, k_colors = "jco",
rect = TRUE, rect_border = "jco", rect_fill = TRUE)

# Forma circular

fviz_dend(hc, cex = 0.5, k = 4,
k_colors = "jco", type = "circular")

# Estilo filogénico

require("igraph")
fviz_dend(hc, k = 4, # Cut in four groups
k_colors = "jco",
type = "phylogenic", repel = TRUE,
phylo_layout = "layout.gem")

9.2 El caso de un dendrograma con data sets largos

# Creación de un dendrograma entero y extracción de sus datos

dend_plot <- fviz_dend(hc, k = 4, 
cex = 0.5, 
k_colors = "jco"
)
dend_data <- attr(dend_plot, "dendrogram") # Extracción dendrograma data

# Corte del dendrograma en alutura h = 

dend_cuts <- cut(dend_data, h = 10)

# Visualición en versión truncada

# Dos ramas
fviz_dend(dend_cuts$upper)

# Gráfica de  dendrograma entero

print(dend_plot)

# Gráfico sub-árbol 1

fviz_dend(dend_cuts$lower[[1]], main = "Subtree 1")

# Gráfico sub-árbol 2
fviz_dend(dend_cuts$lower[[2]], main = "Subtree 2")

# Sub-árbol circular

fviz_dend(dend_cuts$lower[[2]], type = "circular")

9.3 Manipulación de dendrogramas usando dendextend

library(dendextend)
dend <- USArrests[1:5,] %>% # data
scale %>% # Normalización de  data
dist %>% # calculo de matriz de distancia
hclust(method = "ward.D2") %>% # Cluster jerárquico
as.dendrogram # Volviendo al objeto un dendrograma
plot(dend)

# 1. Creación de un dendrograma personalizado

mycols <- c("#2E9FDF", "#00AFBB", "#E7B800", "#FC4E07")
dend <- as.dendrogram(hc) %>%
set("branches_lwd", 1) %>% 
set("branches_k_color", mycols, k = 4) %>% 
set("labels_colors", mycols, k = 4) %>% 
set("labels_cex", 0.5) 

# 2. Creación de gráfico
fviz_dend(dend)
## Warning: `guides(<scale> = FALSE)` is deprecated. Please use `guides(<scale> =
## "none")` instead.

Bibliografía

Everitt, Brian S, Sabine Landau, Morven Leese, and Daniel Stahl. 2011. “Cluster Analysis 5th Ed.” John Wiley.
Galili, Tal. 2015. “Dendextend: An r Package for Visualizing, Adjusting, and Comparing Trees of Hierarchical Clustering.” Bioinformatics. https://doi.org/10.1093/bioinformatics/btv428.
Galili, Tal, and Gregory Jefferis. 2021. Dendextend: Extending Dendrogram Functionality in r. https://CRAN.R-project.org/package=dendextend.
“How to Write Multi-Level (Bullet) Lists in a Table Using Rmarkdown and Pandoc.” n.d. https://stackoverflow.com/questions/31049691/how-to-write-multi-level-bullet-lists-in-a-table-using-rmarkdown-and-pandoc.
Jain, Anil K. 2008. “Data Clustering: 50 Years Beyond k-Means.” In Joint European Conference on Machine Learning and Knowledge Discovery in Databases, 3–4. Springer.
Kassambara, Alboukadel. 2017. Practical Guide to Cluster Analysis in r: Unsupervised Machine Learning. Vol. 1. Sthda.
Kassambara, Alboukadel, and Fabian Mundt. 2020. Factoextra: Extract and Visualize the Results of Multivariate Data Analyses. http://www.sthda.com/english/rpkgs/factoextra.
Maechler, Martin, Peter Rousseeuw, Anja Struyf, and Mia Hubert. 2021. Cluster: "Finding Groups in Data": Cluster Analysis Extended Rousseeuw Et Al. https://svn.r-project.org/R-packages/trunk/ cluster/.
R Core Team. 2021. R: A Language and Environment for Statistical Computing. Vienna, Austria: R Foundation for Statistical Computing. https://www.R-project.org/.
Zhu, Hao. 2021. kableExtra: Construct Complex Table with Kable and Pipe Syntax. https://CRAN.R-project.org/package=kableExtra.