Escalamiento multidimensional (MDS) con R

El escalamiento multidimensional es una técnica que a través de un conjunto de mediciones de la distancia o similaridad entre observaciones trata de organizar los datos en un espacio de \(N\) dimensiones. Generalmente se toman dos dimensiones para poder representarlas mediante un gráfico.

Para entender mejor ésta técnica lo mejor es ponerse manos a la obra con ella. Veremos cómo se puede aplicar el modelo con R, usando un conjunto de datos con las distancias entre ciudades españolas.

#Cargamos los datos en R
df <- read.table(RutaDatos, header = TRUE,
                 fill = TRUE, sep = ",")

#Preparamos los datos
#Hacemos que las provincias sean el nombre de fila
rownames(df) <- df$X
df$X <- NULL
df <- as.dist(df) #Los convertimos en una matriz de distancias

En éste punto tenemos los datos listos. Tenemos una matriz con tantas filas y columnas como ciudades tengamos. Cada celda representa la distancia entre la ciudad de la fila y la ciudad de la columna.

Para aplicar la técnica usamos la librería MASS. Lo primero es comprobar que se puede organizar los datos en el espacio de manera satisfactoria. Al usar la función isoMDS() obtenemos una medida de ajuste, el stress, a la que podemos acceder mediante la propiedad $stress del objeto resultante.

library(MASS)
#Aplicamos el escalamiento multidimensional
#Con k = 2 le decimos que proyecte los datos en 2 dimensiones
mds <- isoMDS(df, k = 2, trace = FALSE)

stress_mds <- round(mds$stress, 2)

Cualquier valor de stress por debajo del 10% implica que el modelo está funcionando razonablemente bien, mientras que un valor por debajo del 5% sería ideal. En nuestro caso, obtenemos un 6.25%, que está bastante bien.

El stress decrece a medida que vamos aumentando el número de dimensiones \(k\). Podemos comparar el ajuste para diferentes valores del parámetro. De ésta forma, será más fácil ver cuántas dimensiones son necesarias para organizar nuestros datos.

#Aplicamos el modelo con diferentes valores de k
Resultados <- rep(NA, 4)
for(i in 1:length(Resultados)){
  Resultados[i] = isoMDS(df, k = i,
              trace = FALSE)$stress
}

#Representamos los valores de ajuste
plot(Resultados, type = "b",
     xlab = "K", ylab = "% stress")
  abline(h = 5, col = "darkgreen")

Vemos que el ajuste mejora enormemente cuando pasamos de 1 a 2 dimensiones, y a partir de ahí se establiza. Por norma general, éste es un buen criterio para seleccionar el número de dimensiones: si el ajuste mejora mucho al añadir dimensiones seguimos añadiendo, hasta que llegue el punto en el que las mejoras se vuelven insignificantes o alcancemos un valor inferior al 5-10%.

Como sabemos que tenemos un buen ajuste con 2 dimensiones, podemos representarlo en un gráfico.

library(ggplot2)
library(reshape2)

DatosGrafico <- data.frame(
  Dim1 = mds$points[, 1], 
  Dim2 = mds$points[, 2]
)
DatosGrafico <- DatosGrafico
ggplot(DatosGrafico, aes(x = Dim2, y = Dim1)) +
  geom_point() + 
  labs(x = "Dimensión 2",
       y = "Dimensión 1",
       title = "Espacio bidimensional") +
  geom_text(label = rownames(DatosGrafico),
            vjust = -0.5,
            size = 5) +
  theme(text = element_text(size = 22),
        plot.title = element_text(hjust = 0.5))

Vemos que reconstruye bastante bien el mapa de España

Si el ajuste no fuese bueno con 2 dimensiones, no podríamos fiarnos demasiado del gráfico. Por ejemplo, imaginemos que necesitamos 3 dimensiones para obtener un buen ajuste. En éste caso, para representar los datos necesitaríamos un gráfico de 3 dimensiones.

Se puede hacer pero es algo más complicado, con plotly se pueden hacer gráficos tridimensionales que te permiten moverte en un espacio 3D. Si el numero de dimensiones es superior a 3 ya tendrás que empezar a echarle imaginación.

Ocurre lo mismo en el análisis de componentes principales (PCA). Es frecuente representar los datos en un espacio de dos dimensiones para interpretar los resultados, pero si el porcentaje de varianza explicada con 2 componentes no es bueno se debería evitar.

Conclusiones

El escalamiento multidimensional nos permite representar un conjunto de observaciones en el espacio a partir de una matriz de las distancias o similaridad que hay entre ellas. En éste caso hemos utilizado distancias entre ciudades, pero también se pueden utilizar otros inputs, como por ejemplo una matriz de correlaciones.

También se podría aplicar en el análisis de texto, sobre una matriz de similaridad entre textos. Hay varias maneras de evaluar las similaridades entre un par de textos, como el índice de Jaccard o la similaridad coseno.

En cualquiera de éstas situaciones, el escalamiento multidimensional puede ser una técnica interesante para visualizar la organización espacial de nuestros datos. Aquellos elementos que sean más parecidos o que estén más cerca apareceran más próximos en el gráfico.