Análisis de correspondencias con R: aplicación a datos de encuestas

II Seminario Análisis de datos avanzados en Ciencias de la Salud, Facultad de Ciencias de la Salud de la Universidad Rey Juan Carlos, Campus de Alcorcón.

Sesión impartida por Emilio López Cano, 24 de mayo de 2018

Las diapositivas del seminario se encuentran en: http://emilio.lcano.com/p/seminariourjc18/

Más ejemplos y explicaciones en mi libro de apuntes Análisis de datos con R (licencia CC)

Preparando el entorno

Descarga e instala R y RStudio en tu sistema, y en ese orden. Puedes encontrar las instrucciones y los archivos de instalación en las siguientes direcciones:

Después de instalar R y RStudio, abre RStudio y ejecuta el siguiente código en la consola de RStudio:

install.packages(c("usethis", "readxl", "FactoMineR", "factoextra", 
                   "dplyr", "gplots", "corrplot", "knitr"))
usethis::use_course("https://goo.gl/p3DU1Y")

En la consola se mostrarán mensajes de confirmación para descargar los materiales en un fichero zip. Tras confirmar, el fichero se descarga y descomprime automáticamente en la carpeta de usuario y se abre el proyecto RStudio con el que trabajaremos, incluido código y datos, que hay que descomprimir:

unzip("datos.zip")

Descripción e importación de datos

Vamos a trabajar con la última Encuesta europea de salud en España (EESE) que elabora el Instituto Nacional de Estadística. Se realiza con periodicidad quinquenal, y la más reciente disponible es la de 2014. Esta encuesta contiene bastantes variables cualitativas adecuadas para realizar análisis de correspondencias, y obviamente de interés para la investigación en Ciencias de la Salud. En la web del INE podemos encontrar y descargar los documentos metodológicos:

El INE publica los resultados de la encuesta después de su tratamiento. Pero además, el pone a disposición los microdatos de la encuesta, lo que es realmente interesante para la investigación académica. Los microdatos contienen las respuestas de cada cuestionario, con un formato determinado que se detalla en los documentos que acompañan a los datos. En el caso de la EESE, disponemos de ficheros en dos formatos:

  • Texto plano TXT con las columnas de ancho fijo

  • Formato Excel, una columna para cada variable

La descripción de las variables y posición en el fichero txt se encuentran en el fichero Excel de diseño de registro. Para este seminario vamos a importar los datos del fichero excel, cuya importación en R es trivial con el paquete readxl:

library(readxl)
eese <- read_excel("datos/MICRODAT.ADULTO.xlsx")

Tras la importación, tenemos un data frame en el espacio de trabajo de R con el que podemos trabajar. Contiene 22842 observaciones (encuestas) de 429 variables (respuestas a preguntas del cuestionario):

dim(eese)
## [1] 22842   429

Para este seminario vamos a seleccionar algunas variables cualitativas como ejemplo. Siguiendo las mismas pautas que se dan a continuación se pueden analizar cualesquiera otras variables de interés. Del mismo modo, el tratamiento y análisis de otras encuestas, ya sean microdatos publicados o de encuestas propias realizadas en las consultas médicas u hospitales, se realizaría de forma similar. Lo más eficiente es guardar los datos originales de la encuesta en un fichero excel con una fila por encuesta y una columna por variable e importar los datos a un data frame de R.

Seleccionamos las variables:

  • E4: Convivencia en pareja
  • G21: Estado de salud percibido en los últimos 12 meses
  • T112: Frecuencia con la que realiza alguna actividad física en su tiempo libre
  • V121: ¿Fuma actualmente?
  • W127: Frecuencia de consumo de alcohol en los últimos 12 meses

La codificación de las preguntas se deduce del propio cuestionario: letra del apartado y nº de pregunta, que se puede comprobar también en el fichero de diseño de registro. En este punto es importante señalar que los microdatos de encuestas suelen incluir una variable de homogeneización, llamada “factor de elevación”, que viene a representar la ponderación que se le asigna a cada individuo que contesta la encuesta. Para facilitar la exposición no tendremos en cuenta este factor de elevación en los ejemplos, que sí habría que tener en cuenta, junto con el resto de la metodología aplicada, en una investigación rigurosa.

Preparación de los datos

Vamos a trabajar con un data frame que contiene solo las variables de interés:

library(dplyr)
## 
## Attaching package: 'dplyr'
## The following objects are masked from 'package:stats':
## 
##     filter, lag
## The following objects are masked from 'package:base':
## 
##     intersect, setdiff, setequal, union
datos <- eese %>% 
  select(convivencia = E4, 
         estado.salud = G21, 
         actividad = T112,
         fuma = V121,
         alcohol = W127)

Que tiene la siguiente estructura:

str(datos)
## Classes 'tbl_df', 'tbl' and 'data.frame':    22842 obs. of  5 variables:
##  $ convivencia : chr  "3" "1" "1" "1" ...
##  $ estado.salud: chr  "4" "1" "2" "2" ...
##  $ actividad   : chr  "1" "2" "2" "1" ...
##  $ fuma        : chr  "4" "4" "3" "1" ...
##  $ alcohol     : chr  "01" "04" "04" "01" ...

Es decir, 22842 observaciones de 5 variables, todas ellas tipo carácter (chr). Esta sería una muestra de las primeras filas:

knitr::kable(head(datos, 10))
convivencia estado.salud actividad fuma alcohol
3 4 1 4 01
1 1 2 4 04
1 2 2 3 04
1 2 1 1 01
1 1 3 3 04
1 2 2 3 01
3 1 3 4 09
3 2 1 1 06
3 3 4 4 04
1 2 1 1 03

Vemos que los valores de las variables son códigos, cuyo significado aparece tanto en la encuesta como en el archivo de diseño de registro. Las variables cualitativas en R son de tipo factor, en vez de carácter, por lo que vamos primero a convertir estas variables en factores:

datos <- datos %>% transmute_all(as.factor)

Ahora cada variable es un factor con varios niveles:

str(datos)
## Classes 'tbl_df', 'tbl' and 'data.frame':    22842 obs. of  5 variables:
##  $ convivencia : Factor w/ 5 levels "1","2","3","8",..: 3 1 1 1 1 1 3 3 3 1 ...
##  $ estado.salud: Factor w/ 5 levels "1","2","3","4",..: 4 1 2 2 1 2 1 2 3 2 ...
##  $ actividad   : Factor w/ 6 levels "1","2","3","4",..: 1 2 2 1 3 2 3 1 4 1 ...
##  $ fuma        : Factor w/ 6 levels "1","2","3","4",..: 4 4 3 1 3 3 4 1 4 1 ...
##  $ alcohol     : Factor w/ 11 levels "01","02","03",..: 1 4 4 1 4 1 9 6 4 3 ...

Pero los códigos de los niveles no nos dicen mucho. Vamos a etiquetar estos niveles de forma más descriptiva para que las salidas y gráficos sean interpretables fácilmente. Vamos a asignar como valores perdidos (NA) los valores “No sabe” o “No contesta” en las encuestas. De nuevo, esto lo hacemos para centrarnos en la explicación del análisis de correspondencias. En una investigación rigurosa habría que analizar el efecto de estos valores faltantes.

levels(datos$convivencia) <- c("cónyuge", "pareja", "no", NA, NA)
levels(datos$estado.salud) <- c("Muy bueno", "Bueno", "Regular", "Malo", "Muy malo")
levels(datos$actividad) <- c("ninguna", "ocasional", "mensual", "semanal", NA, NA)
levels(datos$fuma) <- c("mucho", "poco", "ex", "nunca", NA, NA)
levels(datos$alcohol) <- c("diario", "semanal", "semanal", "semanal", "mensual", 
                           "mensual", "anual", "ex", "nunca",  NA, NA)

Quedando nuestro data.frame final en:

str(datos)
## Classes 'tbl_df', 'tbl' and 'data.frame':    22842 obs. of  5 variables:
##  $ convivencia : Factor w/ 3 levels "cónyuge","pareja",..: 3 1 1 1 1 1 3 3 3 1 ...
##  $ estado.salud: Factor w/ 5 levels "Muy bueno","Bueno",..: 4 1 2 2 1 2 1 2 3 2 ...
##  $ actividad   : Factor w/ 4 levels "ninguna","ocasional",..: 1 2 2 1 3 2 3 1 4 1 ...
##  $ fuma        : Factor w/ 4 levels "mucho","poco",..: 4 4 3 1 3 3 4 1 4 1 ...
##  $ alcohol     : Factor w/ 6 levels "diario","semanal",..: 1 2 2 1 2 1 6 3 2 2 ...

Asociación de variables

Vamos a estudiar el factor estado de salud con el resto de atributos, para ver en cuál o cuáles hay alguna relación. Tomemos a modo de ejemplo el consumo de alcohol, veamos en primer lugar la tabla de frecuencias (la guardamos primero en un objeto para utilizarlo después):

freqs <- table(datos$estado.salud, datos$alcohol)
freqs
##            
##             diario semanal mensual anual   ex nunca
##   Muy bueno    535    1091     952   502  331   796
##   Bueno       2062    2625    2061  1365 1084  1954
##   Regular      878     728     695   623  889  1364
##   Malo         249     135     172   157  453   508
##   Muy malo      60      29      49    48  177   222

El paquete gplots permite visualizar gráficamente la tabla de frecuencias:

library(gplots)
## 
## Attaching package: 'gplots'
## The following object is masked from 'package:stats':
## 
##     lowess
balloonplot(freqs, label = FALSE, show.margins = FALSE,
            main = "Consumo de alcohol vs. Estado de salud")

Para contrastar la relación entre ambos atributos, realizamos el test de la chi-cuadrado. De nuevo guardamos el objeto para acceder posteriormente a él:

ct1 <- chisq.test(freqs)
ct1
## 
##  Pearson's Chi-squared test
## 
## data:  freqs
## X-squared = 1640.9, df = 20, p-value < 2.2e-16

Para que el contraste sea potente debemos tener un número alto de observaciones, típicamente más de 30, y que los valores esperados sean más de cinco en cada celda, lo que se cumple sobradamente:

ct1$expected
##            
##                 diario   semanal   mensual      anual         ex     nunca
##   Muy bueno  698.39817  850.4807  725.1603  497.40568  541.51698  894.0383
##   Bueno     1851.16188 2254.2690 1922.0970 1318.41471 1435.33535 2369.7220
##   Regular    859.42652 1046.5744  892.3591  612.09156  666.37352 1100.1750
##   Malo       277.89839  338.4133  288.5472  197.92182  215.47407  355.7452
##   Muy malo    97.11503  118.2627  100.8364   69.16623   75.30008  124.3196

De igual modo podemos repetir el análisis para el resto de variables cualitativas que teníamos, o realizar un bucle para simplemente ver el p-valor y comprobar en cuáles hay relación o no:

for (atributo in c("convivencia", "actividad", "fuma", "alcohol")){}
sapply(datos[, c(1, 3:5)], function(x){
  atributo <- factor(x)
  chisq.test(table(datos$estado.salud, atributo))$p.value
})
##  convivencia    actividad         fuma      alcohol 
## 1.122581e-25 0.000000e+00 9.470356e-33 0.000000e+00

Lo que nos indica que todos están relacionados con el estado de salud. Cuando el tamaño de la muestra es tan grande, suele ser habitual que siempre se encuentre asociación.

Volver a la presentación

Análisis de correspondencias simple

La primera opción que tenemos para realizar el análisis de correspondencias con R es la función ca del paquete ca. No obstante, ya que el paquete FactoMineR tiene más funcionalidad, vamos a utilizar las funciones de este paquete directamente. Cargamos el paquete y realizamos el análisis con la función CA:

library(FactoMineR)
corres1 <- CA(freqs)

Automáticamente obtenemos el gráfico con la representación de las dos primeras dimensiones. Vemos que la primera dimensión ya explica casi toda la relación entre los atributos. A primera vista, la buena percepción del propio estado de salud se relaciona con algún consumo de alcohol, regular con los que nunca bebieron, y malo con los ex bebedores.

Como hemos guardado el objeto, podemos obtener los resultados numéricos con la función genérica summary:

summary(corres1)
## 
## Call:
## CA(X = freqs) 
## 
## The chi square of independence between the two variables is equal to 1640.89 (p-value =  0 ).
## 
## Eigenvalues
##                        Dim.1   Dim.2   Dim.3   Dim.4
## Variance               0.066   0.005   0.001   0.000
## % of var.             92.158   6.662   1.104   0.076
## Cumulative % of var.  92.158  98.820  99.924 100.000
## 
## Rows
##             Iner*1000    Dim.1    ctr   cos2    Dim.2    ctr   cos2  
## Muy bueno |    11.838 | -0.218 13.205  0.740 | -0.129 64.034  0.259 |
## Bueno     |    11.213 | -0.144 15.214  0.900 |  0.046 21.907  0.094 |
## Regular   |    12.234 |  0.227 17.571  0.953 |  0.026  3.136  0.012 |
## Malo      |    22.278 |  0.547 33.096  0.986 | -0.015  0.343  0.001 |
## Muy malo  |    14.424 |  0.735 20.914  0.962 | -0.141 10.581  0.035 |
##            Dim.3    ctr   cos2  
## Muy bueno -0.005  0.567  0.000 |
## Bueno      0.012  8.299  0.006 |
## Regular   -0.043 53.450  0.035 |
## Malo       0.063 36.827  0.013 |
## Muy malo   0.016  0.857  0.000 |
## 
## Columns
##             Iner*1000    Dim.1    ctr   cos2    Dim.2    ctr   cos2  
## diario    |     3.502 | -0.034  0.297  0.056 |  0.141 68.919  0.944 |
## semanal   |    18.233 | -0.299 27.212  0.990 | -0.020  1.720  0.005 |
## mensual   |     8.703 | -0.213 11.828  0.902 | -0.069 17.283  0.095 |
## anual     |     0.738 | -0.062  0.689  0.619 |  0.029  2.091  0.136 |
## ex        |    28.139 |  0.465 41.955  0.989 | -0.006  0.102  0.000 |
## nunca     |    12.673 |  0.237 18.019  0.943 | -0.047  9.885  0.037 |
##            Dim.3    ctr   cos2  
## diario     0.000  0.001  0.000 |
## semanal    0.020 10.169  0.004 |
## mensual    0.007  1.202  0.001 |
## anual     -0.038 21.394  0.230 |
## ex         0.048 37.572  0.011 |
## nunca     -0.033 29.662  0.019 |

Vemos que automáticamente nos ha proporcionado el resultado del contraste chi-cuadrado, por lo que podemos evitar realizarlo previamente. La primera tabla nos porporciona los autovalores de cada dimensión. El número de dimensiones es el menor número de categorías menos uno (en este caso hay 5 categorías fila y 6 categorías columna, por lo que el número de dimensiones es 5-1=4). Aquí nos fijamos en el porcentaje de varianza acumulado, y vemos que incluso con una dimensión sería suficiente. Después tenemos, para cada atributo (fila y columna) las inercias de cada nivel de atributo, y para cada dimensión su coordenada y dos medidas más: la contribución a esa coordenada concreta y la medida de calidad cos2.

Vamos a ver algunas visualizaciones interesantes para interpretar los resultados numéricos. Utilizamos algunas funciones del paquete factoextra. La primera de ellas nos sirve para seleccionar el número de dimensiones que necesitamos para explicar la mayor parte posible de la variabilidad. Es un gráfico de sedimentación, al que en este caso añadimos un criterio utilizado para esta selección (máximo entre los inversos del número de categorías menos uno, en este caso 25%).

max.porc <- max(1/(dim(freqs)-1)*100)
library(factoextra)
## Loading required package: ggplot2
## Welcome! Related Books: `Practical Guide To Cluster Analysis in R` at https://goo.gl/13EFCZ
fviz_screeplot(corres1) +
 geom_hline(yintercept = max.porc, linetype = 2, color = "red") + 
  labs(title = "Gráfico de sedimentación", x = "Dimensiones", 
       y = "Porcentaje de variabilidad explicada")

Si necesitáramos más de dos dimensiones, deberiamos plantearnos si no podemos reagrupar los factores, para lo cual podemos visualizarlos con alguna de las medidas disponibles, y así detectar afinidades

fviz_ca_row(corres1, col.row = "cos2",
             gradient.cols = c("#00AFBB", "#E7B800", "#FC4E07"), 
             repel = TRUE)

fviz_ca_col(corres1, col.col = "cos2",
             gradient.cols = c("#00AFBB", "#E7B800", "#FC4E07"), 
             repel = TRUE)

En nuestro caso, como ya sabíamos, no es necesario. Ahora podemos ver para cada atributo cuál es la contribución de sus categorías a las dos dimensiones principales:

fviz_contrib(corres1, choice = "row", axes = 1:2)

fviz_contrib(corres1, choice = "col", axes = 1:2)

La línea discontinua nos indica cuál sería la contribución si fueran homogéneas.

En el siguiente gráfico (del paquete corrplot) lo podemos visualizar para cada dimensión por separado:

library(corrplot)
## corrplot 0.84 loaded
corrplot(corres1$row$contrib, is.corr = FALSE)    

corrplot(corres1$col$contrib, is.corr = FALSE)    

Por último, tenemos una visualización de intervalos de confianza en forma de elipses para ver si realmente los niveles de los atributos se solapan:

ellipseCA(corres1)

Donde vemos que tenemos más confianza para concluir cuáles son las relaciones.

Con el resto de atributos se puede realizar el mismo análisis. A modo de ejemplo veamos simplemente el gráfico perceptual:

CA(table(datos$estado.salud, datos$convivencia))

## **Results of the Correspondence Analysis (CA)**
## The row variable has  5  categories; the column variable has 3 categories
## The chi square of independence between the two variables is equal to 136.753 (p-value =  1.122581e-25 ).
## *The results are available in the following objects:
## 
##    name              description                   
## 1  "$eig"            "eigenvalues"                 
## 2  "$col"            "results for the columns"     
## 3  "$col$coord"      "coord. for the columns"      
## 4  "$col$cos2"       "cos2 for the columns"        
## 5  "$col$contrib"    "contributions of the columns"
## 6  "$row"            "results for the rows"        
## 7  "$row$coord"      "coord. for the rows"         
## 8  "$row$cos2"       "cos2 for the rows"           
## 9  "$row$contrib"    "contributions of the rows"   
## 10 "$call"           "summary called parameters"   
## 11 "$call$marge.col" "weights of the columns"      
## 12 "$call$marge.row" "weights of the rows"
CA(table(datos$estado.salud, datos$actividad))

## **Results of the Correspondence Analysis (CA)**
## The row variable has  5  categories; the column variable has 4 categories
## The chi square of independence between the two variables is equal to 2262.139 (p-value =  0 ).
## *The results are available in the following objects:
## 
##    name              description                   
## 1  "$eig"            "eigenvalues"                 
## 2  "$col"            "results for the columns"     
## 3  "$col$coord"      "coord. for the columns"      
## 4  "$col$cos2"       "cos2 for the columns"        
## 5  "$col$contrib"    "contributions of the columns"
## 6  "$row"            "results for the rows"        
## 7  "$row$coord"      "coord. for the rows"         
## 8  "$row$cos2"       "cos2 for the rows"           
## 9  "$row$contrib"    "contributions of the rows"   
## 10 "$call"           "summary called parameters"   
## 11 "$call$marge.col" "weights of the columns"      
## 12 "$call$marge.row" "weights of the rows"
CA(table(datos$estado.salud, datos$fuma))

## **Results of the Correspondence Analysis (CA)**
## The row variable has  5  categories; the column variable has 4 categories
## The chi square of independence between the two variables is equal to 183.1837 (p-value =  9.470356e-33 ).
## *The results are available in the following objects:
## 
##    name              description                   
## 1  "$eig"            "eigenvalues"                 
## 2  "$col"            "results for the columns"     
## 3  "$col$coord"      "coord. for the columns"      
## 4  "$col$cos2"       "cos2 for the columns"        
## 5  "$col$contrib"    "contributions of the columns"
## 6  "$row"            "results for the rows"        
## 7  "$row$coord"      "coord. for the rows"         
## 8  "$row$cos2"       "cos2 for the rows"           
## 9  "$row$contrib"    "contributions of the rows"   
## 10 "$call"           "summary called parameters"   
## 11 "$call$marge.col" "weights of the columns"      
## 12 "$call$marge.row" "weights of the rows"

También podríamos analizar dos atributos cualesquiera, por ejemplo el tabaco y el alcohol:

CA(table(datos$alcohol, datos$fuma))

## **Results of the Correspondence Analysis (CA)**
## The row variable has  6  categories; the column variable has 4 categories
## The chi square of independence between the two variables is equal to 2341.438 (p-value =  0 ).
## *The results are available in the following objects:
## 
##    name              description                   
## 1  "$eig"            "eigenvalues"                 
## 2  "$col"            "results for the columns"     
## 3  "$col$coord"      "coord. for the columns"      
## 4  "$col$cos2"       "cos2 for the columns"        
## 5  "$col$contrib"    "contributions of the columns"
## 6  "$row"            "results for the rows"        
## 7  "$row$coord"      "coord. for the rows"         
## 8  "$row$cos2"       "cos2 for the rows"           
## 9  "$row$contrib"    "contributions of the rows"   
## 10 "$call"           "summary called parameters"   
## 11 "$call$marge.col" "weights of the columns"      
## 12 "$call$marge.row" "weights of the rows"

Volver a la presentación

Análisis de correspondencias múltiple

Veamos ahora un análisis conjunto de todos los atributos mediante el análisis de correspondencias múltiple. De nuevo vamos a usar el paquete FactoMineR. La función MCA por defecto utiliza los valores perdidos como una categoría. Podemos eliminar todas las encuestas que tengan algún valor perdido, pero estaríamos perdiendo información de los atributos que sí la tienen. El argumento na.method admite el valor “average”, que imputa los valores perdidos con un promedio.

corres2 <- MCA(datos,  method = "Burt", na.method = "average")

Esta función produce dos gráficos: un mapa perceptual con todas las categorías de todas las variables, y otro solo con las variables, donde se pueden identificar las relaciones más fuertes entre atributos.

En general en un análisis de correspondencias múltiple las primeras dimensiones no van a explicar tanta varianza como en el simple, y es posible que tengamos que explorar más de dos dimensiones.

summary(corres2)
## 
## Call:
## MCA(X = datos, method = "Burt", na.method = "average") 
## 
## 
## Eigenvalues
##                        Dim.1   Dim.2   Dim.3   Dim.4   Dim.5   Dim.6
## Variance               0.101   0.076   0.053   0.046   0.042   0.041
## % of var.             14.113  10.574   7.399   6.428   5.811   5.724
## Cumulative % of var.  14.113  24.687  32.086  38.514  44.325  50.049
##                        Dim.7   Dim.8   Dim.9  Dim.10  Dim.11  Dim.12
## Variance               0.041   0.040   0.040   0.038   0.037   0.036
## % of var.              5.696   5.626   5.535   5.362   5.148   5.086
## Cumulative % of var.  55.745  61.372  66.907  72.268  77.416  82.501
##                       Dim.13  Dim.14  Dim.15  Dim.16  Dim.17
## Variance               0.033   0.031   0.026   0.018   0.017
## % of var.              4.650   4.272   3.626   2.588   2.362
## Cumulative % of var.  87.151  91.424  95.050  97.638 100.000
## 
## Individuals (the 10 first)
##                        Dim.1    ctr   cos2    Dim.2    ctr   cos2    Dim.3
## 1                   | -0.829  0.009  0.159 | -0.218  0.001  0.011 |  0.508
## 2                   |  0.474  0.003  0.095 |  0.314  0.002  0.042 | -0.336
## 3                   |  0.635  0.006  0.198 | -0.637  0.006  0.200 | -0.328
## 4                   |  0.148  0.000  0.009 | -0.793  0.010  0.257 |  0.455
## 5                   |  1.044  0.015  0.272 |  0.068  0.000  0.001 |  0.155
## 6                   |  0.417  0.002  0.077 | -1.124  0.020  0.562 | -0.550
## 7                   |  0.014  0.000  0.000 |  1.245  0.025  0.423 | -0.135
## 8                   |  0.119  0.000  0.006 |  0.186  0.001  0.014 |  0.724
## 9                   |  0.216  0.001  0.013 |  0.685  0.007  0.136 | -0.145
## 10                  |  0.366  0.002  0.060 | -0.306  0.001  0.042 |  0.677
##                        ctr   cos2  
## 1                    0.005  0.060 |
## 2                    0.002  0.048 |
## 3                    0.002  0.053 |
## 4                    0.004  0.084 |
## 5                    0.000  0.006 |
## 6                    0.006  0.135 |
## 7                    0.000  0.005 |
## 8                    0.010  0.213 |
## 9                    0.000  0.006 |
## 10                   0.009  0.205 |
## 
## Categories (the 10 first)
##                         Dim.1     ctr    cos2  v.test     Dim.2     ctr
## cónyuge             |   0.054   0.299   0.015   8.417 |  -0.264   9.457
## pareja              |   0.628   2.611   0.067  17.625 |   0.136   0.164
## no                  |  -0.110   1.071   0.047 -14.951 |   0.291  10.054
## Muy bueno           |   0.361   4.785   0.139  25.978 |   0.462  10.419
## Bueno               |   0.196   3.727   0.176  28.993 |  -0.082   0.880
## Regular             |  -0.353   5.622   0.175 -28.931 |  -0.121   0.888
## Malo                |  -0.756   8.330   0.214 -32.155 |  -0.223   0.967
## Muy malo            |  -1.044   5.549   0.138 -25.588 |  -0.036   0.009
## actividad_ninguna   |  -0.386  10.975   0.397 -44.835 |  -0.067   0.444
## actividad_ocasional |   0.057   0.258   0.011   7.031 |  -0.135   1.934
##                        cos2  v.test     Dim.3     ctr    cos2  v.test  
## cónyuge               0.352 -40.955 |  -0.099   1.905   0.050 -15.375 |
## pareja                0.003   3.820 |   0.895  10.120   0.136  25.121 |
## no                    0.330  39.658 |   0.047   0.379   0.009   6.442 |
## Muy bueno             0.227  33.183 |   0.048   0.160   0.002   3.445 |
## Bueno                 0.031 -12.196 |  -0.044   0.366   0.009  -6.576 |
## Regular               0.021  -9.953 |  -0.207   3.697   0.060 -16.987 |
## Malo                  0.019  -9.482 |   0.508   7.194   0.097  21.635 |
## Muy malo              0.000  -0.881 |   0.877   7.462   0.097  21.486 |
## actividad_ninguna     0.012  -7.803 |   0.299  12.615   0.239  34.803 |
## actividad_ocasional   0.060 -16.678 |  -0.320  15.546   0.335 -39.547 |
## 
## Categorical variables (eta2)
##                       Dim.1 Dim.2 Dim.3  
## convivencia         | 0.063 0.270 0.143 |
## estado.salud        | 0.445 0.181 0.217 |
## actividad           | 0.381 0.136 0.334 |
## fuma                | 0.179 0.382 0.289 |
## alcohol             | 0.519 0.405 0.167 |

Con el gráfico de sedimentación podemos tomar alguna decisinó al respecto:

fviz_screeplot(corres2, addlabels = TRUE)

Por ejemplo, a partir de la tercera dimensión ya no ganamos mucho. A partir de aquí podemos hacer las mismas visualizaciones que habíamos visto para el análisis simple, por ejemplo:

fviz_mca_var(corres2, col.var = "contrib",
             gradient.cols = c("#00AFBB", "#E7B800", "#FC4E07"), 
             repel = TRUE, # avoid text overlapping (slow)
             ggtheme = theme_minimal()
             )

Y utilizar la tercera dimensión también:

fviz_mca_var(corres2, axes = c(1,3),
             repel = TRUE, choice = "var",
             ggtheme= theme_minimal())

fviz_mca_var(corres2, axes = c(2,3), 
             repel = TRUE, choice = "var",
             ggtheme= theme_minimal())

fviz_mca_var(corres2, axes = c(1,3),
             col.var = "contrib",
             gradient.cols = c("#00AFBB", "#E7B800", "#FC4E07"), 
             repel = TRUE, # avoid text overlapping (slow)
             ggtheme = theme_minimal()
             )

fviz_mca_var(corres2, axes = c(2,3),
             col.var = "contrib",
             gradient.cols = c("#00AFBB", "#E7B800", "#FC4E07"), 
             repel = TRUE, # avoid text overlapping (slow)
             ggtheme = theme_minimal()
             )

A medida que ganamos complejidad es más importante el conocimiento del problema para interpretar las dimensiones.

Más allá con R

En este seminario hemos visto cómo realizar análisis de correspondencias de datos de encuestas. Se propone profundizar en los siguientes temas para sacar todo el partido a R.

  1. Análisis con el factor de elevación. Para crear tablas de frecuencias estimadas de toda la población, podemos usar la función xtabs:
addmargins(xtabs(as.numeric(eese$FACTORADULTO)%/%1000 ~ SEXOa + E4, data = eese))
##      E4
## SEXOa        1        2        3        8        9      Sum
##   1   11260104   867033  6808880    14747    49421 19000185
##   2   10569367   782995  8496567      216    99021 19948166
##   Sum 21829471  1650028 15305447    14963   148442 38948351

Esto nos sirve para el análisis de correspondencias simple, pero el múltiple solo acepta como entrada data frames, por lo que habría que usar otros paquetes.

  1. Análisis longitudinal. En el caso de encuestas es muy común que se repitan con cierta periodicidad. En el caso de la que hemos utilizado es quinquenal, pero solo tenemos dos porque anteriormente se utilizaba la encuesta nacional (no europea). Cuando tenemos este tipo de datos longitudinales, se pueden realizar animaciones de los mapas perceptuales para ver la evolución en el tiempo de las asociaciones. Se pueden ver algunos ejemplos aquí: https://www.r-graph-gallery.com/animation/

  2. Informes reproducibles. Trabajar con el código e ir viendo las salidas está bien durante la investigación. Pero a la hora de presentar resultados, debemos plasmarlos en un formato adecuado (informe, artículo, etc.) Se pueden crear fácilmente informes en R que incluyan el tratamiento y análisis de datos, código, y cualquier otro contenido (texto formateado, imágenes, etc.). Aunque hay varias formas, la más sencilla y cómoda es utilizando ficheros R Markdown, que puede generar ficheros HTML, PDF y Microsoft Word. Este propio archivo es un fichero .Rmd, en el que además de gráficos y salida textual se ha incluido una tabla formateada.