library(tidyverse)# Manipulación de datos y gráficososlibrary(lubridate)# Manipulación de fechas y tiempoolibrary(readxl)# Lectura de archivos de excel (.xls o .xlsx)library(janitor)# Lo usamos para editar los nombres de las bases de datos
Introducción a R
Generalidadles
R Discrimina minúsculas de mayúsculas
Los comentarios en R se denotan con el “#”
Ecosistema R Markdown y Quarto
Publicación de documentos en Rpubs
Acceso rápido
Ctrl + Enter: ejecutar línea de código
Ctrl + L: limpiar consola
Ctrl + Alt + i: insertar fragmento de R a documentos R Markdown o Quarto.
CTRL + Shift + K: Compilar documentos desde .Rmd o .qmd
[1] enero febrero marzo abril mayo junio enero
Levels: abril enero febrero junio marzo mayo
El orden en el que asignó los meses es incorrecto, ya que aparece de primero el mes de “abril”. Podemos reordenar los niveles a través del arguemnto “levels” de la función factor():
---title: "Fundamentos de R"author: "Edimer David Jaramillo"format: html: toc: true toc-title: "Tabla de contenido" smooth-scroll: true code-fold: true df-print: paged toc-location: left number-depth: 4 theme: light: flatly dark: darkly code-copy: true highlight-style: github code-tools: source: true code-link: true ---```{r setup, include=FALSE}knitr::opts_chunk$set(echo =TRUE, warning =FALSE, message =FALSE)```# Fuente de imágenes- Todas las imágenes fueron tomadas de las siguientes fuentes: - [R for Data Science](https://r4ds.had.co.nz/index.html) - [Functional Programming](https://dcl-prog.stanford.edu/) - [Advanced R 2nd](https://adv-r.hadley.nz/index.html)# Bibliotecas R```{r}library(tidyverse) # Manipulación de datos y gráficoslibrary(lubridate) # Manipulación de fechas y tiempolibrary(readxl) # Lectura de archivos de excel (.xls o .xlsx)library(janitor) # Lo usamos para editar los nombres de las bases de datos```# Introducción a R## Generalidadles- R Discrimina minúsculas de mayúsculas- Los comentarios en R se denotan con el "\#"- Ecosistema R Markdown y Quarto- Publicación de documentos en *Rpubs*## Acceso rápido- `Ctrl + Enter`: ejecutar línea de código- `Ctrl + L`: limpiar consola- `Ctrl + Alt + i`: insertar fragmento de R a documentos R Markdown o Quarto.- `CTRL + Shift + K`: Compilar documentos desde *.Rmd* o *.qmd*- `CTRL + Shift + M`: Insertar tubería desde RStudio## Asignación<center><imgsrc="https://d33wubrfki0l68.cloudfront.net/bd90c87ac98708b1731c92900f2f53ec6a71edaf/ce375/diagrams/name-value/binding-1.png"/></center># Tipos de datos<center><imgsrc="https://d33wubrfki0l68.cloudfront.net/1d1b4e1cf0dc5f6e80f621b0225354b0addb9578/6ee1c/diagrams/data-structures-overview.png"width="300/"/></center><br><br><center><imgsrc="https://d33wubrfki0l68.cloudfront.net/baa19d0ebf9b97949a7ad259b29a1c4ae031c8e2/8e9b8/diagrams/vectors/summary-tree-s3-1.png"width="300"/></center>## Vectores atómicos<center><imgsrc="https://dcl-prog.stanford.edu/images/data-structure-basics/vector.png"width="700"/></center>### Numéricos```{r}dato_numerico1 <-22.50# 0 dimensiones```- ¿Cómo crear un vector numérico?```{r}vector_num <-c(22.1, 10, 50.2) # 1 dimensión``````{r}vector_num +50```- Podemos consultar el tipo de datos a través de las funciones **class()** y **typeof**:```{r}class(vector_num)typeof(vector_num)```- Podemos consultar la longitud de una varialbe:```{r}length(vector_num)```### Texto```{r}dato_texto1 <-"universidad"class(dato_texto1)typeof(dato_texto1)```- Podemos crear un vector de texto:```{r}vector_texto1 <-c("nombre", 'apellido', "ciudad")class(vector_texto1)typeof(vector_texto1)```- Puedo consultar la longitud:```{r}length(vector_texto1)```- ¿Cómo puedo contar cuántas letras tiene cada elemento del vector de texto?```{r}nchar(vector_texto1)```- ¿Qué pasa con el espacio en blanco? ¿También se cuenta?```{r}texto1 <-"ciudad"texto2 <-"ciudad "nchar(texto1)nchar(texto2)```### Enteros```{r}entero1 <-20class(20)``````{r}entero1``````{r}entero1 +50```- ¿Cómo puedo almacenar un número de naturaleza discreta (entero)?```{r}entero2 <- 20Lclass(entero2)typeof(entero2)```- También puedo crear un vector de número enteros:```{r}entero3 <-c(10L, 20L, 30L)class(entero3)typeof(entero3)```### Factores<center><imgsrc="https://d33wubrfki0l68.cloudfront.net/1c19eabc59d445cab78fc605053c7393ec630e15/5843b/diagrams/vectors/factor.png"width="500"/></center>- Los factores representan variables cualitativas ordinales- Podemos controlar el orden de los elementos- Por defecto R siempre organizará el texto de manera alfabética```{r}meses <-c("enero", "febrero", "marzo", "abril", "mayo", "junio", "enero")class(meses)```- Puedo pasar la variable "meses" a *factor* con la función **factor()**:```{r}meses_factor1 <-factor(meses)class(meses_factor1)``````{r}mesesmeses_factor1```- El orden en el que asignó los meses es incorrecto, ya que aparece de primero el mes de "abril". Podemos reordenar los niveles a través del arguemnto **"levels"** de la función **factor()**:```{r}mes_ordenado <-factor(meses, levels =c("enero", "febrero", "marzo", "abril","mayo", "junio"))mes_ordenado```### Lógicos- Los lógicos representan dos estados: TRUE (1) o FALSE (0)```{r}logico1 <-TRUEclass(logico1)```- También es común (no lo recomiendo) ver el TRUE o FALSE como T y F, respectivamente```{r}logico2 <- Tclass(logico2)``````{r}logico3 <-FALSEclass(logico3)```- ¿Qué pasa si agregamos el TRUE o FALSE entre comillas?```{r}otro <-"TRUE"class(otro)```- ¿Qué pasa si sumo dos TRUE?```{r}TRUE+TRUETRUE+TRUE-FALSETRUE*4TRUE/2vector_logico <-c(TRUE, FALSE, TRUE, FALSE, TRUE, FALSE)class(vector_logico)```- ¿Qué ocurre si comparo dos números para saber si son iguales?```{r}2==22==32==2.000000000000001```- ¿Cómo sumo un vector de números o de lógicos? La función **sum()** nos permite sumar elementos de un vector numérico o lógico```{r}sum(vector_logico)```- ¿Qué pasa si comparo una letra con otra letra?```{r}"a"=="a"```- ¿Qué pasa si la comparación se hace entre mayúscula y minúscula?```{r}"A"=="a""A">"a""A"<"a"```### Fechas/Tiempo- Las fechas en R se representan como *Date* y cuando las generamos manualmente se incorporan dentro de comillas:```{r}fecha0 <-"2022-01-01"class(fecha0)```- ¿Cómo forzar a R para que entienda la fecha como *Date*? **Rta//** as.Date():```{r}fecha1 <-as.Date(fecha0)class(fecha1)```- ¿Puedo sumarle un número a fecha0 y fecha1?```{r}#fecha0 + 1 fecha1 +1```- Podemos extraer información alternativa de las fechas con la biblioteca *lubridate*: - Año: year() - Mes: month() - Día del mes: day() - Semana del año: week() - Día de la semana: weekdays(). Esta función **no es del paquete lubridate**.```{r}# Añoyear(fecha1)# Mes como número enteromonth(fecha1, label =FALSE)# Mes como texto abreviadno (ene = enero)month(fecha1, label =TRUE, abbr =TRUE)# Mes como texto completo (enero)month(fecha1, label =TRUE, abbr =FALSE)# Día del mesday(fecha1)# Semana del añoweek(fecha1)# Día de la semanaweekdays(fecha1)```- ¿Cómo almacenar año-mes-día-hora-minutos-segundos? - hora: hour() - minutos: minute() - segundos: second()```{r}tiempo <-"2022-10-06 07:38:42"class(tiempo)```- ¿Cómo hacer la conversión al tipo POSIXct?```{r}# Esto no funciona porque pierdo horas-minutos-segundosas.Date(tiempo)ymd(tiempo)# Ejecución correctatiempo_bien1 <-ymd_hms(tiempo)tiempo_bien2 <-as.POSIXct(tiempo)class(tiempo_bien1)class(tiempo_bien2)```- ¿Qué pasa si nos dan la fecha en orden diferente (día-mes-año): "28-10-2022" o con texto (día-mes-año): "01-julio-2022"?```{r}fecha_mal1 <-"28-10-2022"fecha_mal2 <-"01-julio-2022"class(fecha_mal1)```- La biblioteca "lubridate" proporciona funciones intuitivas para trabajar con fechas:```{r}fecha_bien1 <-dmy(fecha_mal1)class(fecha_bien1)dmy(fecha_mal2)```- También es posible tener un vector de fechas:```{r}vector_fechas1 <-c("2010-01-01", "2020-01-01", "2030-01-01")class(vector_fechas1)vector_fechas2 <-ymd(vector_fechas1)class(vector_fechas2)```### Datos especiales- `NA`: no disponible o ausente (**Not Available**)- `NaN`: por ejemplo una indeterminación (**NOT a NUMBER**)- `Inf` o `-Inf`: infinito y menos infinito```{r}mi_na <-NAclass(mi_na)NA+1NA-1NA*1NA/1```- También podemos crear un vector de NA:```{r}vector_na <-c(NA, NA, NA)length(vector_na)```- Puedo tener vectores con valores "reales" y valores ausentes:```{r}vector_mixto <-c(1, 12, NA, 24, NA)class(vector_mixto)1+ vector_mixto# quiero sumar los elementos del vector_mixto# siempre devuelve NAsum(vector_mixto)```- Podemos corregir el "problema" de respuestas en NA agregando el argumento **na.rm = TRUE**:```{r}sum(vector_mixto, na.rm =TRUE)```- Infinito, -Infinito y NaN:```{r}-Inf+Inf0/0```# Tubería %\>%```{r}# El operador de tubería está en el tidyverse (magrittr)mi_vector <-c(1, 20, 40, 50)sum(mi_vector)mi_vector %>%sum()mi_vector %>%sum()```# Coerción- ¿Qué pasa si mezclo en un mismo vector números y texto?```{r}vector_mezclado <-c(12, 21, 24, "12m")vector_mezclado %>%class()vector_mezclado```- Hay dos tipos de coerción: - Implícita: es cuando R toma la decisión de manera autónoma. Por ejemplo cuando decide tratar el vector anterior como un "character" - Explícita: el usuario ejerce control sobre la coerción o conversión.## `character` → `factor`- as.factor() o factor()```{r}orden_carrera <-c("primero", "segundo", "tercero", "primero")orden_carrera %>%class()carrera_factor <- orden_carrera %>%as.factor()carrera_factor %>%class()carrera_factor```## `character` → `numeric`- as.numeric()```{r}texto_num1 <-"24.5"texto_num1 %>%class()texto_num2 <- texto_num1 %>%as.numeric()texto_num2 %>%class()```- ¿Cómo corregir el siguiente problema? ¿Cómo llevar "texto_num3" a numeric?```{r}texto_num3 <-"24,5"texto_num3 %>%as.numeric()c("12.8", "14,5") %>%as.numeric() ```- Para solucionar el problema simplemente reemplazaos la coma "," por el punto ".", a través de la función `str_replace_all()````{r}corregido <-str_replace_all(string = texto_num3,pattern =",",replacement =".")corregido```- Ahora sí podemos hacer la coerción:```{r}corregido_numero <- corregido %>%as.numeric()corregido_numero %>%class()```## `character` → `date`- as.Date()```{r}"2020-10-21"%>%as.Date() %>%class()```- Vimos anteriormente que podemos usar las funciones de la biblioteca `lubridate()`:```{r}"2020-10-21"%>%ymd() %>%class()```## `character` → `logical`- as.logical()```{r}"TRUE"%>%as.logical() %>%class()```# Confirmación## `is.numeric()` o `is.double()````{r}2%>%is.numeric()``````{r}c(1, 20, 201.5, 40.5) %>%is.numeric()```## `is.integer()````{r}1L %>%is.integer()``````{r}1%>%is.integer()```## `is.character()````{r}"Hola mundo"%>%is.character()```## `is.factor()````{r}nuevo_factor <-factor(c("lunes", "martes", "miércoles"))nuevo_factor %>%is.factor()```## `is.logical()````{r}FALSE%>%is.logical()```## `is.na()`, `is.nan()`, `is.infinite()````{r}NA%>%is.na()NaN%>%is.nan()NA%>%is.nan()NaN%>%is.na()Inf%>%is.infinite()-Inf%>%is.infinite()```# Matrices- Podemos crear una matriz con la función `matrix()`: en este caso se hace por filas```{r}mi_matriz1 <-matrix(data =c(10, 20, 30, 40, 50, 60),nrow =2,ncol =3,byrow =TRUE)mi_matriz1```- Podemos crear una matriz con la función `matrix()`: en este caso se hace por columnas```{r}mi_matriz2 <-matrix(data =c(10, 20, 30, 40, 50, 60),nrow =2,ncol =3,byrow =FALSE)mi_matriz2```- Sumar dos matrices:```{r}mi_matriz1 + mi_matriz2```- Restar dos matrices:```{r}mi_matriz1 - mi_matriz2```- Número de filas:```{r}mi_matriz1 %>%nrow()mi_matriz2 %>%nrow()```- Número de columnas:```{r}mi_matriz1 %>%ncol()mi_matriz2 %>%ncol()```- Dimensiones (filas y columnas):```{r}mi_matriz1 %>%dim()mi_matriz2 %>%dim()```- Multiplicación de matrices:```{r}matriz3 <-matrix(data =c(1, 2, 3, 4, 5, 6, 7, 8),nrow =2,ncol =4,byrow =TRUE)matriz4 <-matrix(data =c(10, 20, 30, 40, 50, 60, 70, 80),nrow =4,ncol =2,byrow =TRUE)```- ¿se pueden multiplicar?```{r}matriz3 %>%ncol() == matriz4 %>%nrow()``````{r}matriz_mult <- matriz3 %*% matriz4matriz_mult```- La inversa de una matriz:```{r}matriz_mult %>%solve()```- Transpuesta de una matriz:```{r}# También aplica para un vectormatriz_mult %>%t()```- Diagonal de una matriz:```{r}matriz_mult %>%diag()```- Matriz con texto:```{r}matriz_texto <-matrix(data =c("Cali", "Medellín", "Bucaramanga", "Pasto"),nrow =2,ncol =2)matriz_texto %>%class()matriz_texto %>%is.character()```# Listas<center><imgsrc="https://d33wubrfki0l68.cloudfront.net/5ba72e78f2df8568c1be82236659558b0e06904c/04521/diagrams/lists-structure.png"width="500"/></center>- Creamos las listas con la función `list()````{r}lista1 <-list(1, "a", NA, c(20, 30), list("ciudad", "departamento"))lista1 %>%class()```- Podemos consultar el número de elementos de una lista:```{r}lista1 %>%length()```# Base de datos- `dataframe` o `tibble`<center><imgsrc="https://dcl-prog.stanford.edu/images/data-structure-basics/tibble.png"width="500"/></center>### Dataframes internos- R trae consigo bases de datos para ejemplos. Para consultar las bases de datos disponibles podemos ejecutar la función `data()````{r}iris %>%class()Titanic %>%class()```### Dataframes manuales- Podemos crear manualmente las bases de datos. Esto se hace a través de vectores.```{r}datos_manuales <-data.frame(ciudad =c("Cali", "Bogotá", "Manizales", "Miami"),habitantes =c(12, 15, 24, 54),colombia =c(TRUE, TRUE, TRUE, FALSE),fecha =c("2021-01-01", "2021-01-01", "2021-01-01", NA))datos_manuales```- Podemos consultar las dimensiones de la base de datos:```{r}datos_manuales %>%dim()```- Podemos consultar los nombres de las columnas:```{r}datos_manuales %>%names()```- ¿Cómo accedemos a una sola variable? múltiples formas```{r}# Una formadatos_manuales$habitantes# Otra formadatos_manuales[["habitantes"]]# Otra formadatos_manuales %>%pull(habitantes)```- ¿Cómo cambiar los nombres a las variables?```{r}datos_manuales %>%names()``````{r}datos_manuales2 <- datos_manuales %>%set_names(c("var1", "var2", "var3", "var4"))datos_manuales2```### Dataframes importados```{r}encuesta <-read_excel("Encuesta-Respuestas.xlsx")encuesta```- ¿Cómo cambiar el nombre de una manera más rápida?```{r}encuesta %>%clean_names()```- Podemos darle nuestros propios nombres:```{r}mis_nombres <-str_c("pregunta", 1:11)encuesta2 <- encuesta %>%set_names(mis_nombres)encuesta2```# Secuencias y repeticiones```{r}-10:1seq(from =1, to =10, by =2)rep("pregunta", 10)str_c("pregunta", 1:11)```# Atributos<center><imgsrc="https://d33wubrfki0l68.cloudfront.net/f00424fe1681465cdf5c4495f3de907598c89d81/a5523/diagrams/vectors/data-frame-2.png"width="250"/></center><center><imgsrc="https://d33wubrfki0l68.cloudfront.net/c5fd25550aa2a82d2483069c1eb4de6a3a1f763f/c821f/diagrams/vectors/data-frame-1.png"width="250"/></center>```{r}encuesta2 %>%attributes()```# Operadores## Aritméticos- Suma: `+`- Resta: `-`- Multiplicación: `*`- División: `/`## Relacionales- Igualdad: `==`- Diferencia: `!=`- Negación: `!`- Disyunción (o): `|`- Conjunción (y): `&`# Subconjuntos<center><imgsrc="https://dcl-prog.stanford.edu/images/vector-subset.png"/></center>## Vectores- Si tomamos la pregunta 7 de la encuesta:```{r}pregunta7 <- encuesta2$pregunta7pregunta7```- ¿cómo obtenemos un subconjunto (vector) de aquellos que eligieron un número mayor a 5?```{r}pregunta7[pregunta7 >5]```- ¿Cuántos estudiantes eligieron un número al azar mayor a 5?```{r}pregunta7[pregunta7 >5] %>%length()```- Si tomamos la pregunta 1, ¿está tipificada de la manera correcta?```{r}encuesta2$pregunta1 %>%class()``````{r}pregunta1 <- encuesta2$pregunta1 %>%as.numeric()pregunta1```- ¿Cuántos estudiantes superan el promedio del promedio académico?```{r}# Rta:promedio <- pregunta1 %>%mean()pregunta1[pregunta1 > promedio] %>%length()```- Si tomamos la pregunta 4:```{r}pregunta4 <- encuesta2$pregunta4pregunta4```- ¿Cómo obtenemos el subconjunto (vector) de personas que respondieron "Sí"?```{r}# Rta:pregunta4[pregunta4 =="Sí"] %>%length()```## Base de datos### Seleccionar columnas- ¿Cómo seleccionar sólo las preguntas 10 y 11?```{r}encuesta_p10p11 <- encuesta2 %>%select(pregunta10, pregunta11)encuesta_p10p11```### Filtrar filas- ¿Cómo filtrar una o más filas?```{r}encuesta2 %>%slice(1, 29)```- ¿Cómo filtrar una o más filas que cumplan con alguna condición?```{r}encuesta2 %>%filter(pregunta4 =="Sí")```- ¿Cómo filtrar una o más filas que cumplan con más de una condición?```{r}encuesta2 %>%filter(pregunta4 =="Sí") %>%filter(pregunta8 =="Sí")```- ¿Cómo filtrar filas de personas que usen motocicleta y transporte público?```{r}encuesta2 %>%filter(pregunta5 %in%c("Transporte público", "Motocicleta"))```- ¿Cuántos estudiantes se movilizan en algún medio de transporte que no sea a pie?```{r}encuesta2 %>%filter(pregunta5 !="A pie")```## Matrices```{r}otra_matriz <-matrix(data = pregunta1,ncol =10,nrow =3)otra_matriz```- ¿Cómo extraer la fila 2?```{r}otra_matriz[2, ]```- ¿Cómo extraer la columna 1?```{r}otra_matriz[, 1]```- ¿Cómo extraer el elemento que está en la fila 1 y columna 10?```{r}otra_matriz[1, 10]```- ¿Cómo extraer la fila 1 y 3 con las columnas 6 y 10?```{r}# Rta:```## Listas```{r}otra_lista <-list(e1 =1,e2 =2,e3 ="a",e4 =c(10, 20, 30),e5 = pregunta1 )otra_lista```- ¿Cómo acceder a algún elemento de la lista?```{r}otra_lista$e1```- El proceso anterior es equivalente a:```{r}otra_lista[1]otra_lista[[1]]```- ¿Cómo acceder a la última respuesta (3.80) de la pregunta 1 que está dentro de la lista anterior?```{r}otra_lista$e5[29]```- El proceso anterior es equivalente a:```{r}otra_lista[[5]][29]otra_lista[["e5"]][29]```# Análisis de texto## Conteo de palabras p10<center><imgsrc="https://www.tidytextmining.com/images/tmwr_0101.png"width=600/></center>```{r}library(wordcloud)library(tidytext)library(tm)stop_words_spanish <-data.frame(word =stopwords("spanish"))conteo_p10 <- encuesta_p10p11 %>%select(pregunta10) %>%unnest_tokens(word, pregunta10) %>%anti_join(stop_words_spanish) %>%count(word, sort =TRUE)conteo_p10```## Nube de palabras p10```{r}wordcloud(words = conteo_p10$word,freq = conteo_p10$n,max.words =100,random.order =FALSE,colors =c("blue", "green"))```