Profesor del programa de Ingeniería Industrial, Universidad Sergio Arboleda. Candidato a doctor en Ingeniería de la Universidad de los Andes.
R es un entorno y lenguaje de programación con un enfoque al análisis estadístico. A través de este curso veremos cuáles son las funcionalidades y herramientas con las cuales podrás desarrollar tareas tan sencillas como sumas y restas hasta modelos de analítica de datos que usan compañías como Airbnb, Uber o Twitter.
En este curso haremos una introducción a los conceptos básicos para el manejo de datos y el desarrollo de análisis estadísticos básicos. Así pues, ¡empecemos!
En su forma más sencilla, R puede ser utilizado como una calculadora interactiva.
5+7
## [1] 12
R simplemente imprime el resultado 12 por defecto. Sin embargo, R es un lenguaje de programación y, en ocasiones, la utilizamos porque queremos automatizar procesos o evitar repeticiones innecesarias.
En este caso, queremos usar este resultado más adelante. En lugar de volver a escribir todo el código, crearemos una variable que guarde el resultado. La expresión que utilizaremos para esto es <-.
x <- 5 + 7
Notarán que R no imprime el resultado en este momento. Cuando se asigna información, R asume que no necesita mostrar el resultado. Para ver el resultado, solamente hay que nombrar la variable.
x
Con R puedes realizar la mayoría de las operaciones básicas. Estas expresiones van a depender del tipo de datos que utilicemos, lo cual lo veremos a lo largo de esta sesión. Cualquier objeto que contenga datos en R se llama estructura de datos y la primera que veremos serán los vectores numéricos.
La forma más sencilla de crear vectores es con la función c() que significa concatenar o combinar. Probemos unir las expresiones x+3, 5, 23 y asignarlo a la variable z
z <- c (x + 3, 5, 23)
Los vectores numéricos, como en la primera expresión, tambien pueden incluir expresiones y podemos realizar operaciones con ellas. Probemos multiplicar el vector por 2 y sumarle 100.
z*2 + 100
## [1] 130 110 146
Como pueden ver, R aplicó las operaciones a cada elemento del vector. Otras operaciones disponibles son +, -, /, and ^. Para realizar una raíz cuadrada, use la función sqrt(). Probemos la raíz cuadrada de z -1 y asignarlo a la variable rc_z
rc_z <- sqrt(z-1)
rc_z
¿Y qué pasa si dividimos vectores entre si? Probemos que pasa si dividimos z entre su raíz cuadrada.
z/rc_z
En efecto, divide el valor de cada elemento de z por el de la misma posición. ¿ Y qué pasa si son de diferente longitud? Recicla los elementos! Probemos un ejemplo.
a <- c (1, 2, 3, 4)
b <- c (0, 10)
c <- a + b
c
Probemos otro ejemplo:
a <- c (1, 2, 3, 4)
b <- c (0, 10, 100)
c <- a + b
## Warning in a + b: longitud de objeto mayor no es múltiplo de la longitud de
## uno menor
c
En el caso de que no sean de igual longitud, el sistema sacará una alerta. Finalmente, si queremos hacer operaciones con los elementos dentro de un vector. Por ejemplo, podemos sumar sus elementos o contar sus elementos. Veamos un ejemplo:
sum(a)
length(a)
Otras funciones que podrían ser útiles son min(), max(), mean(), median(), unique() y sort()
EJERCICIO Usted ha sido escogido por el director del área de producción de su compañía para realizar un análisis de la demanda mensual de la empresa y realizar una estimación de las variaciones de la demanda, de acuerdo con la información del área de mercadeo. La información que posee es la siguiente:
¿En cuál de los escenarios presentados se venden, en promedio, más unidades al final del año?
La siguiente estructura de datos que nos interesa son las listas. Las listas contienen valores de cualquier tipo simple (numerico o no numérico), y podrían ser estructuras completas (lista de listas). Si usamos como referencia a una hoja de calculo con datos sobre individuos, una lista podria ser una fila que tiene los datos de los individuos. Para crear una lista, el comando que utilizaremos es list(). Veamos un ejemplo:
DetailStudent=list(fullName="Fred Meyers", age=40,female=FALSE)
El objeto ‘DetailStudent’ almacena temporalmente la lista en la computadora. Los nombres de las variables pueden contener letras del alfabeto y números (y algunos caracteres de puntuación), pero no debe comenzar con un número.
En el codigo anterior, solo se ha pedido crear la lista. R lo ejecuta y nada mas, no tienes que esperar ningun mensaje ni resultado. Si quieres ver lo que has creado, escribelo de manera explicita, así:
DetailStudent
## $fullName
## [1] "Fred Meyers"
##
## $age
## [1] 40
##
## $female
## [1] FALSE
Nota que hay varios tipos de datos en la lista:
fullName es texto o caracteres. age es un numero. female es un valor lógico.
Para acceder a cada uno de los elemento tu lista:
#Opción 1: La posición del dato
DetailStudent[[1]]
## [1] "Fred Meyers"
#Opción 2: El nombre de la variable
DetailStudent[['fullName']]
## [1] "Fred Meyers"
#Opción 3: Usar el signo de dolar (o peso)
DetailStudent$fullName
## [1] "Fred Meyers"
Hasta el momento creamos y consultamos una lista. ¿Cómo cambiamos la información de una lista? Si queremos cambiar un valor de la lista, solamente debemos asignar el valor
DetailStudent$fullName='Camilo Pinto'
¿Y si queremos es añadir un elemento a nuestra lista? Funciona igual que nuestro caso anterior, asignando el valor a este elemento
DetailStudent$city = 'Seattle'
Si queremos dejarlo vacío debemos asignar el comando NA o eliminarlo con NULL. ¿Y si ya no necesito la lista? Para eliminar una lista necesio usar rm()
list1=list(1,2,3,4)
rm(list1)
EJERCICIO Como parte de su práctica en la escuela de Ingeniería, el decano le solicite que organice la información de los casos disciplinarios a revisar en el próximo comité. Es necesario que la información que :
Crea un objeto tipo lista con los datos de los estudiantes. Los nombres son Freddy Patiño, Luis Ferrucho, Danna Rodriguez y Pedro Meléndez. Cada uno está en un semestre mayor que el anterior, empezando en tercer semestre. Además, todos están acusados de fraude y el estado del proceso es activo.
Antes de llegar al comité se decidió que a todos se les agregaría si hubo confesión. En los estudiantes que hay, solamente Pedro confesó su pena.
3.Después del comité se decidió que todos los estudiantes que no confesaron serán suspendidos por un semestre y los que confesaron recibirán una amonestación escrita.
Los vectores deben contener un único tipo de datos. En un archivo de Excel, un vector puede ser una columna.
names=c("Fred Meyers","Sarah Jones", "Lou Ferrigno","Sky Turner")
ages=c(40,35, 60,77)
female=c(F,T,T,T)
Los tres objectos almacenas temporalmente listas. Los nombre pueden contener letras del alfabeto y números (y algunos caracteres de puntuación), pero no debe comenzar con un número.
Si quieres acceder a ciertos elementos solamente debemos usar corchetes cuadrados simples:
names[1]
## [1] "Fred Meyers"
# o también
ages[1]
## [1] 40
# o también
female[1]
## [1] FALSE
Podemos alterar el vector al asignar nueva información de esta manera (igual que en las listas):
names[1]='Alfred Mayer'
Para añadir un nuevo elemento, usaremos una estructura recursiva:
elements=c(1,2,3)
elements=c(elements,40)
Sin embargo, para eliminar los datos no podemos utilizar la operación Null que usamos en las listas. Para eliminar el elemento debemos encoger el vector usando la siguiente expresión:
elements= elements[-4]
¿Y qué podemos hacer si tenemos valores repetidos en nuestro vector? En este caso, podemos usar la función unique:
weekdays=c('M','T','W','Th','S','Su','Su')
weekdays
## [1] "M" "T" "W" "Th" "S" "Su" "Su"
unique(weekdays)
## [1] "M" "T" "W" "Th" "S" "Su"
¿Y cómo hacemos para saber qué tipo de datos tenemos? ¿Es un vector o es una lista? Para esto, la función que nos interesa es str. Dependiendo del tipo de datos que tengamos, podremos obtener:
str(elements)
str(DetailStudent)
str(rc_z)
Además, cuando crees y uses operaciones debes considerar cuáles aplican para cada estructura. Probemos la operación length:
listTest=list(1,2,3,3)
vectorTest=c(1,2,3,4,4)
length(listTest)
length(vectorTest)
Los Data frames pueden interpretarse como estructuras compuestas a partir de las estructuras simples. Si partieramos de usar vectores, cada uno corresponde a las columnas. Para crear un data frame, el comando es `data.frame:
# Usaremos cuatr vectores sobre estudiantes extranjeros
names=c("Qing", "Françoise", "Raúl", "Bjork")
ages=c(32,33,28,30)
country=c("China", "Senegal", "Spain", "Norway")
education=c("Bach", "Bach", "Master", "PhD")
#DF es una composición de vectores:
DF_vectors=data.frame(names,ages,country,education)
DF_vectors
## names ages country education
## 1 Qing 32 China Bach
## 2 Françoise 33 Senegal Bach
## 3 Raúl 28 Spain Master
## 4 Bjork 30 Norway PhD
¿Y si tenemos listas? Usaremos el comando data.list en conjunto con do.call. La forma de aplicarla es así:
# Listas por fila
row1=list(name="Qing", age=32, country="China", deg="Bach")
row2=list(name="Françoise", age=33, country="Senegal", deg="Bach")
row3=list(name="Raúl", age=28, country="Spain", deg="Master")
row4=list(name="Bjork", age=30, country="Norway", deg="PhD")
# lista de listas
dataList=list(row1,row2,row3,row4)
#DF es una composición de listas:
DF_lists=do.call(rbind.data.frame,dataList)
row.names(DF_lists)=NULL
DF_lists
## name age country deg
## 1 Qing 32 China Bach
## 2 Françoise 33 Senegal Bach
## 3 Raúl 28 Spain Master
## 4 Bjork 30 Norway PhD
Y ¿qué tipo de cosas nos interesa saber de un data frame?
#Conocer si es un Data Frame
str(DF_vectors)
str(DF_lists)
#Dimensiones del Data Frame
dim(DF_vectors)
#Filas del Data Frame
nrow(DF_vectors)
#Columnas del Data Frame
length(DF_vectors)
#Ver las primeras filas
head(DF_vectors,2)
#Ver las últimas filas
tail(DF_vectors,2)
#¿Qué variables tenemos?
names(DF_vectors)
Al leer los datos, la estructura que deben tener en cuenta es [Filas, columnas]. Para leer las columnas, tenemos varias opciones:
#Puedo tomar una columna si sé la columna
DF_vectors$names
## [1] Qing Françoise Raúl Bjork
## Levels: Bjork Françoise Qing Raúl
#Puedo tomar una columna si sé su posición
DF_vectors[,1]
## [1] Qing Françoise Raúl Bjork
## Levels: Bjork Françoise Qing Raúl
#Varias columnas (con posiciones)
DF_vectors[,c(1,4)]
## names education
## 1 Qing Bach
## 2 Françoise Bach
## 3 Raúl Master
## 4 Bjork PhD
#Varias columnas (con nombres)
DF_vectors[,c('names','education')]
## names education
## 1 Qing Bach
## 2 Françoise Bach
## 3 Raúl Master
## 4 Bjork PhD
Además, para la lectura de las filas tenemos dos opciones:
#una fila
DF_vectors[2,]
## names ages country education
## 2 Françoise 33 Senegal Bach
#varias filas
DF_vectors[c(2,3),]
## names ages country education
## 2 Françoise 33 Senegal Bach
## 3 Raúl 28 Spain Master
Nótese en los casos anteriores, que si no indicabas filas, tenías toda la fila; y que si no indicas columnas, vienen todas las columnas. Si solo quieres un valor:
students=DF_vectors[1,3]
A veces nos va interesar tomar una parte del Data Frame, esto lo llamaremos subset y lo haremos asignando esta información que obtuvimos:
studentsCopy= DF_vectors
Ahora haremos las modificaciones a los valores que obtenemos:
# cambio el valor de una edad:
studentsCopy[1,2]=23
# No hay advertencia, el cambio ya se hizo:
studentsCopy[1,]
## names ages country education
## 1 Qing 23 China Bach
Podemos tener una nueva columna con valores vacios:
studentsCopy$lastName=NA
studentsCopy
## names ages country education lastName
## 1 Qing 23 China Bach NA
## 2 Françoise 33 Senegal Bach NA
## 3 Raúl 28 Spain Master NA
## 4 Bjork 30 Norway PhD NA
Y puedo eliminarla con NULL:
studentsCopy$lastName=NULL
studentsCopy
## names ages country education
## 1 Qing 23 China Bach
## 2 Françoise 33 Senegal Bach
## 3 Raúl 28 Spain Master
## 4 Bjork 30 Norway PhD
Aunque las estructuras de datos son útiles para trabajar en R, los datos que vamos a utilizar vienen en diferentes formatos de datos. Por tanto, es vital establecer una conexión entre la máquina y R. Este espacio en el cual estaremos trabajando se denomina Workspace y varía entre máquina y máquina. Sin embargo, R hace que funcione en diferentes tipos de computadores.
Lo primero que nos interesa es conocer nuestro actual directorio con la función getwd().
getwd()
## [1] "C:/Users/AndresEsteban/Dropbox/Sergio Arboleda/Curso R/Clases/Clase 1"
Una vez sabemos dónde estamos, queremos saber qué tenemos. Para esto, usamos el comando dir().
dir()
## [1] "Clase 1.csv" "Clase 1.nb.html" "Clase 1.pptx"
## [4] "Clase 1.Rmd" "Clase 1.txt" "Clase 1.xlsx"
## [7] "Clase_1.html" "Clase_1.Rmd" "test.R"
## [10] "testdir"
Si queremos guardar nuestra ubicación actual, solamente debemos asignarlo a una variable.
old.dir <- getwd()
Ahora, sabemos que ahí no está el archivo que necesitamos. Vamos a crear un nuevo directorio que nos lleve a dónde está la información que necesito. Para eso, voy a usar la función dir.create()
dir.create("testdir")
## Warning in dir.create("testdir"): 'testdir' already exists
Recuerden que queremos cambiar tan poco como sea posible la información, o como dicen los creadores de R “Solamente toma foto, deja únicamente huellas”. Por eso, asignaremos nuestro trabajo a esta carpeta con el comando setwd()
setwd("testdir")
Ahora, crearemos y agregaremos archivos a esta carpeta con el comando file.create(). Para empezar crearemos un script de R al que llamaremos test.
file.create("test.R")
## [1] TRUE
En general, pueden revisar todas las funciones asociadas con file como exists, rename, copy, path
Ahora, lo que necesitamos hacer ahora es conseguir la información que tenemos en este directorio. Con el archivo de excel llamado “Clase 1” cargaremos esta información. Carguen este archivo en su directorio.
Hay una serie de formatos de datos comunes que se pueden leer dentro y fuera de R. Esto incluye archivos de texto en formatos como csv, txt, html y json. También incluye archivos de salida de aplicaciones estadísticas como SAS y SPSS. Los recursos en línea que incluyen servicios web y páginas HTML también se pueden leer en R.
La primera función que examinaremos es read.table(). Esta es una función incorporada en R que puede utilizarse para leer varios formatos de archivo en un Data Frame. Esta es probablemente la función interna más común utilizada para leer archivos simples en R.
df = read.table("Clase 1.csv", header = TRUE, sep=",")
La función read.csv() también es una función incorporada en R que es casi idéntica a la read.table(), con la excepción de que los argumentos de encabezado y relleno se establecen en TRUE de forma predeterminada. En este paso, verás lo fácil que es cargar un archivo csv utilizando read.csv().
df2 = read.csv("Clase 1.csv")
La función read.table() se usa con más frecuencia para leer el contenido de un archivo delimitado por tabulaciones. En este paso aprenderás cómo hacerlo.
df3 = read.table("Clase 1.txt", header=TRUE, sep="\t", quote="")
## Warning in read.table("Clase 1.txt", header = TRUE, sep = "\t", quote =
## ""): line 1 appears to contain embedded nulls
## Warning in read.table("Clase 1.txt", header = TRUE, sep = "\t", quote =
## ""): line 2 appears to contain embedded nulls
## Warning in read.table("Clase 1.txt", header = TRUE, sep = "\t", quote =
## ""): line 3 appears to contain embedded nulls
## Warning in read.table("Clase 1.txt", header = TRUE, sep = "\t", quote =
## ""): line 4 appears to contain embedded nulls
## Warning in read.table("Clase 1.txt", header = TRUE, sep = "\t", quote =
## ""): line 5 appears to contain embedded nulls
## Warning in scan(file = file, what = what, sep = sep, quote = quote, dec =
## dec, : embedded nul(s) found in input
En R, la unidad fundamental de código compartible es el paquete. Un paquete agrupa código, datos, documentación y pruebas, y es fácil de compartir con otros. A partir de enero de 2015, había más de 6,000 paquetes disponibles en Comprehensive R Archive Network, o CRAN, la cámara de compensación pública para paquetes de R. Esta gran variedad de paquetes es una de las razones por las que R es tan exitosa: lo más probable es que alguien ya haya resuelto un problema en el que estás trabajando, y puedes beneficiarte de su trabajo al descargar su paquete.
Si estás leyendo este libro, ya sabes cómo usar los paquetes:
Los instalas desde CRAN con install.packages("X"). Los usas en R con library("x"). *Recibes ayuda con package?X y help(package = "x").
En la próxima clase aprenderemos a trabajar con dos paquetes tidyverse() y readr().