Definiciones generales

Proceso a seguir para explorar los datos:

Hay dos tipos de preguntas que siempre sirven para entender los datos:

Terminos importantes a tener claro en el mundo de la estadística:

La variación de variables categóricas

  • La variación es la tendencia que tienen los valores de una variablesa cambiar de una medida a otra

Para poder ver esta variación, hay dos formas de verlo; a través de a distribución y a través de su visualización. Para tratar estos dos sistemas, depende de si es una variable categórica o numérica.

  • variable categórica: factor o vector de carácteres. Vamos a ver como podemos ver su variación:
library(tidyverse)
## -- Attaching packages ----------------------------------------------------------------------------------------------- tidyverse 1.2.1 --
## v ggplot2 3.1.0     v purrr   0.2.5
## v tibble  1.4.2     v dplyr   0.7.8
## v tidyr   0.8.2     v stringr 1.3.1
## v readr   1.1.1     v forcats 0.3.0
## -- Conflicts -------------------------------------------------------------------------------------------------- tidyverse_conflicts() --
## x dplyr::filter() masks stats::filter()
## x dplyr::lag()    masks stats::lag()
ggplot(data = diamonds)+
  geom_bar(mapping = aes(x = cut)) # usaremos barras para ver las variaciones

Si queremos contar los valores por barra, con una tibble, usaremos la función count():

diamonds %>%
  count(cut) # conteo de los valores de la variable discreta

variable continua: conjunto infinito de valores ordenados (números, fechas).

Podemos usar un histograma de frecuencias:

ggplot(data = diamonds) +
  geom_histogram(mapping = aes(x = carat), binwidth = .5)

También podemos usar la función count() con coutwidth() para saber las frequancias en número:

diamonds %>%
  count(cut_width(carat, .5)) # cut_width nos ayudaa a medir diferentes anchuas para trabajar mejor. Diferentes anchuras pueden mostrar diferentes patrones. 

Para ver mas información, podemos hacerlo de la siguiente manera:

diamonds_filter <- diamonds %>%
  filter(carat<3)
ggplot(data = diamonds_filter)+
  geom_histogram(mapping = aes(x = carat), binwidth = .05)

Este gráfico nos muestra más información para visualizar y entendor los gráficos.

En algunas ocasiones querremos comparar diferentes histogramas en uno solo. En ese caso es mejor usar freqpoly (polígono de frecuencia), que en vez de usar las barras para sacar informaciín, usa polígonos. Ejemplo:

ggplot(data = diamonds_filter, mapping = aes(x = carat, color = cut))+
  geom_freqpoly(binwidth = .1)

En este gráfico podemos ver la variación, y nos debe llevar a empezar a formular preguntas útiles. Para eso debes ser escéptico!

¿Qué preguntes debemos hacernos?

Viendo el anterioir gráfico, ¿qué preguntas nos deberíamos hacer?

En el dataset de diamantes podemos ver datos curioso como por ejemplo; Dado un valor muy alto, los valores decaen:

diamonds_filter <- diamonds %>%
  filter(carat<3)
ggplot(data = diamonds_filter)+
  geom_histogram(mapping = aes(x = carat), binwidth = .01)

¿Cuál podría ser el motivo? Deberíamos saber más sobre los diamentes y su proceso de creación.

Encontrando subgrupos dentro de los datos:

El siguiente paso es agrupar valores similares para detectar subgrupos dentro de la ifnormación. Para detectarlos, se deben hacer 3 preguntas:

  1. ¿Qué determina que los elementos de un cluster sean similares entre ellos?

  2. ¿Qué determina que clusters separados sean diferentes entre si?

  3. Describir y explicar cada uno de los clusters.

  4. ¿Por qué alguna observación puede ser calsificada en un cluster erroneo?

Outliers en la información

Un outlier es una observación que no encaja en ningún patrón, totalmente inusual. Lo normal es que sea un error en la entrada de datos, pero pueden no serlo y ser una información muy relevante. Ejemplo:

ggplot(data = diamonds)+
  geom_histogram(mapping = aes(x = y), binwidth = .5)

¿Cómo podríamos hacer un zoom en estos outliers? Limitaremos el eje de ordenadas entre 0 y 100.

ggplot(data = diamonds)+
  geom_histogram(mapping = aes(x = y), binwidth = .5)+
  coord_cartesian(ylim = c(0,100))

Vamos a extraer los outliers para poder analizarlos:

unusual_diamonds <- diamonds %>%
  filter(y<2 | y>30) %>%
  select(price, x,y,z) %>%
  arrange(y)
unusual_diamonds

Podemos ver que estos valores son muy atípicos, y podemos ver cuales tienen sentido o no.

Si tenen un efecto muy pequeño en la creación del modelo, lo mejor es sustituir los outliers por NA. Es preferible trabajar con un grupo de datos comunes, que no trabajar con datos que contengan outliers. Sin embargo, si aportan explicabilidad en los datos, es mejor incluirlos en el modelo.

Reemplazando errores por NAs

Como debemos tratar los outliers? Tenemos varias opciones:

  1. Eliminar los valores atípicos (opción menos recomendable)
good_diamonds <- diamonds %>%
  filter(between(y, 2.5, 29.5))
  1. Reemplazar los valores atípicos por NAs con la función mutate():
good_diamonds <- diamonds %>%
  mutate(y = ifelse(y < 2 | y > 30, NA, y))

La función ggplot() no incluye los NAs, pero te advierte cuantos hay:

ggplot(data = good_diamonds, mapping = aes(x = x, y = y))+
  geom_point() # podemos usar el parametro na.rm = T para eliminar el WARNING
## Warning: Removed 9 rows containing missing values (geom_point).

¿Cómo podemos entender porqué un valores atípico respecto los otros valores? Si nos vamos en el dataset de flights, podemos mirar si para los vuelos cancelados y no cancelados tene alguna relación con el horario de salida.

Para realizar este análisis crearemos una nueva vaariable que nos diga si es NA o no es NA.

nycflights13::flights %>%
  mutate(
    cancelled = is.na(dep_time),
    sched_hour = sched_dep_time %/% 100, # para quedarme solo con la hora
    sched_min = sched_dep_time %% 100,
    sched_dep_time = sched_hour + sched_min/60
  ) %>%
  ggplot(mapping = aes(sched_dep_time))+
    geom_freqpoly(mapping = aes(color = cancelled), binwidth = 1/4) # que salgan cada 5 munitos

Podemos ver algunos patrones, por ejemplo que en las horas de máximos vuelos hay más vuelos cancelados.

La covariación entre las diferentes variables:

EL concepto de covariación describe el comportamiento entre dos o más variabes para saber si cambian de forma conjunta. El tipo de gráfico depende del tipo de variables utilizadas.

Caso más simple -> categoría vs variable continua: gráfico con el geom_freqpoly()

ggplot(data = diamonds, mapping = aes(x = price))+
  geom_freqpoly(mapping = aes(color = cut), binwidth = 500)

Pero cuando la comparación es complicada por que, por ejemplo, una categoría pesa mucho mas que otra, miraremos la densidad:

ggplot(data = diamonds, mapping = aes(x = price, y = ..density..))+
  geom_freqpoly(mapping = aes(color = cut), binwidth = 500)

Este gráfico sí que nos permite comparar los resutados. Interesante ver que los diamantes estilo “fair”, tienen un precio más caro que los otros, pero estas hipótesisis pueden estar influenciadas por la poca información que nos puede dar el gráfico, es decir, puede que la categoría fer solo tenga 10 observaciones, y una de ellas tenga un precio mas elevado que las otras. Esta imagen nos haría creer que los diamantes fair se suelen vender más caros.

La covariación a través de boxplot

En los boxplots, el 50% de los valores caen dentro de la caja. Está dividido entre quartiles, caja y bigotes. La caja empieza en el 1Quartil (25% de los datos) y va hasta el 3 quartil, 75% de los datos. La distancia entre estos dos quartiles es el rango intercuartílico.

Dentro de la caja, se representa en una linea la mediana, el percentil 50% de la distribución. Nos ayuda a ver por ejemplo si la información es simétrica respecto de la media.

Outliers, datos que caen mas de 1.5 veces mas lejos del rango intercuartílico, de Q3 y de Q1. Son valores atípicos dentro de dicha distribución.

Los bigotes, se extienden desde la caja hasta el punto más cercano al rango intercuartílico por 1.5, que no sea considerado outlier.

¿Cómo usarlo dentro de la caja?

ggplot(data = diamonds, mapping = aes(x = cut, y = price))+
  geom_boxplot()

Además el boxplot nos está mostrando como la categoría está ordenada, ya que vemos que va de fair a ideal, de peor a mejor.

¿Cómo podríamos ordenarlo nosotros mismos en otro caso?

ggplot(data = mpg, mapping = aes(x = class, hwy))+
  geom_boxplot()

Para ordenarlos, usaríamos el siguiente código.

ggplot(data = mpg)+
  geom_boxplot(mapping = aes(x = reorder(class, hwy, FUN = median),y = hwy))+
  coord_flip()

En este caso lo hemos ordenado a partir de la mediana, de menor a mayor.

La covariación de factores a través de heatmaps

En este apartado veremos como podemos visualizar la correlación entre dos variables categóricas. Por eso miraremos cuantas variables categóricas caen en el mismo parta del “mapa”. Ejemplo:

ggplot(data = diamonds) +
  geom_count(mapping = aes(x = cut, y = color))

Pero también se puede hacer un cálculo exacto con dplyr, ¿cómo?:

diamonds %>%
  count(color, cut) # aquí podemos ver el tamaño de las bolas, mas claras que de forma visual

Podemos tambien hacerlo con unas estéticas sobre el count que habamos de hacer:

diamonds %>%
  count(color, cut) %>%
  ggplot(mapping = aes(x = cut, y = color)) +
    geom_tile(mapping = aes(fill = n))

Se pueden usar también otros paquetes para ampliar nuestra capacidad de visualización 3d o más grandes:

La covariación de variables continua con scatterplot

Esta parte nos permitirá analizar la correlación entre dos variables continuas:. Por ejemplo, ¿hay alguna relación entre precio y los kilates?

ggplot(data = diamonds)+
  geom_point(mapping = aes(x = carat, y = price), alpha = .01)

También se pueden usar las bins para mapear la información en dos variables continuas. Usaremos dos funciones de ggplot(), necessitamos un nuevo paquete porque no vienen por defecto. Para isntalarlo library(hexbin):

Las dos funciones dividen el plano coordenado en cajas 2d, y luego utiliza un sistema de color para indicar cuantos punto caen dentro de la subdivisión.

library(hexbin)
ggplot(data = diamonds)+
  geom_bin2d(mapping = aes(x = carat, y = price))

Aquí se muestran que el color es mayor contra más dimantes cean en cada rectángulo.

Y si queremos usar mapas hexagonales:

library(hexbin)
ggplot(data = diamonds)+
  geom_hex(mapping = aes(x = carat, y = price))

Podemos también tratar una variable numérica con una variable categórica, para combinar la con otra variable continua. Ideal para hacer boxplots:

diamonds %>%
  filter(carat<3) %>%
  ggplot(mapping = aes(x = carat, y = price))+
    geom_boxplot(mapping = aes(group = cut_width(carat, 0.1)))

Podemos añadir otro parámetro para aumentar la información que nos dan los boxplots del anterior gráfico, varwidth igual a TRUE. Es un modo de mostrar si la anchura de boxplot es proporcional al numero de puntos, contra más ancho, más puntos:

diamonds %>%
  filter(carat < 3) %>%
  ggplot(mapping = aes(x = carat, y = price))+
    geom_boxplot(mapping = aes(group = cut_width(carat, 0.1)), varwidth = TRUE)

Podemos también hacer las divisiones pero que aproximadamente se lleven el mismo numero de puntos el dataset dentro de cada una de ellas, con el cut_number():

diamonds %>%
  filter(carat < 3) %>%
  ggplot(mapping = aes(x = carat, y = price))+
    geom_boxplot(mapping = aes(group = cut_number(carat, 20))) # 20 cajas se llevan mas o menos el mismo numero de observaciones, para asi entender la dispersion de los datos

Visualizaciones de patrones

Si hay una relación sistemática entre dos variables podróa ser visible con un gráfico. Siempre que veamos un patrón hay preguntas a hacerse:

Por ejemplo, hagamos un scatter plot de los geisers del parque de yellowstone:

ggplot(data = faithful)+
  geom_point(mapping = aes(x = eruptions, y = waiting))

Cuando dos variables tienen una variación conjunta o covariación elevada, se pueden usar los valores de una para predecir los de otra. Si la covariación es debido a una relación causal, que es un tipo de relación causal, se podría tomar los valores de una para predecir la otra.

Los modelos es una forma para extraer patrones de los datos. En el dataset de diamantes, podemos mirar la relación entre precio y kilates para buscar patrones. Vamos a crear un modelo para predecir el precio a partir de los kilates. Para eso cargaremos la librería “modelr” que nos permite crear modelos incluyendo el formato pipe.

library(modelr)
# Creacion de un modelo de regresion lineal
mod <- lm(log(price)~log(carat), data = diamonds) 
mod
## 
## Call:
## lm(formula = log(price) ~ log(carat), data = diamonds)
## 
## Coefficients:
## (Intercept)   log(carat)  
##       8.449        1.676

Hagamos la predicción del precio con el modelo creado:

diamonds_pred <- diamonds %>%
  add_residuals(mod) %>%
  mutate(res = exp(resid))
head(diamonds_pred)
ggplot(data = diamonds_pred) +
  geom_point(mapping = aes(x=carat, y = resid))