Este cuaderno es una guía para facilitar el desarrollo de la actividades en clase de los cursos: Hidroclimatológia (pregrado y posgrado) y Modelación de procesos hidrológicos de la FEAR-PUJ, consolidado con la ayuda de lose studiantes del curso de Modelación de Procesos Hidrológicos 2022-1 y Cristian Díaz (estudiante doctoral en la FEAR-PUJ).
R, también conocido como GNU S, es un entorno y un lenguaje para el cálculo estadístico y la generación de gráficos. R implementa un dialecto del premiado lenguaje S, desarrollado en los Laboratorios Bell por John Chambers et al.2008 (se puede consultar en [https://link.springer.com/book/10.1007/978-0-387-75936-4]).
Para quienes inician con este lenguaje, R provee un acceso relativamente sencillo a una amplia variedad de técnicas estadísticas y gráficas.Para los usuarios avanzados se ofrece un lenguaje de programación completo con el que añadir nuevas técnicas mediante la definición de funciones es de utilidad.
Rstudio es una aplicación que permite interactuar con R de forma más amigable, además de facilitar muchas de las tareas de programación y análisis de datos;es decir, RStudio es una Interfaz Gráfica -GUI (Graphical User Interface).En términos más técnicos, RStudio es un entorno de desarrollo integrado (integrated development environment) para R.
El actual científico jefe de RStudio es Hadley Wickham (http://hadley.nz/). Wickham es uno de los más prolíficos desarrollador de paquetes para R y creadorde un nuevo estilo de programar y analizar datos en R conocido como ‘tidyverse (https://blog.rstudio.org/2016/09/15/tidyverse-1-0-0/)’.
Para instalar R en un computador, vamos a la página web https://cran.r-project.org/. Para descargar R, hacemos clic en Download del sistema operativo de nuestro ordenador, seleccionamos la opción adecuada.
Al hacer clic sobre Download R for Windows seremos redireccionados a la página que pueden veren la siguiente imagen. Para iniciar el proceso, hacemos clic sobre install R for the first time
Una vez que hemos instalado R, descargamos RStudio desde la página web https://www.rstudio.com/, haciendo clic en la palabra Download
luego
seleccionamos el sistema operativo de nuestro ordenador (Windows, Linux
o Mac)
En el desarrollo del curso, usaremos RStudio como la intefaz gráfica de R para facilitar el proceso de interacción con la herramienta.Para iniciar RStudio, hacemos clic en el icono de RStudio y al abrir deberíamos ver algo parecido a:
RStudio está
(normalmente) dividido en 4 paneles:
Script (superior izquierda): esta ventana representa el editor de código. Se trata del lugar donde editamos la sintaxis para posteriormente ejecutarla. Al escribir allí no sucederá nada, a no ser que se apriete algún botón para ejecutar los comandos (RUN) o las teclas ctrl+enter.
Consola (inferior izquierda): Corresponde a lo que sería el software R en su versión básica. Allí el software ejecuta las operaciones realizadas desde el editor de sintaxis o las escritas directamente.
Entorno e historia (superior derecha): en este lugar se muestra el conjunto de datos y los “objetos” (resultados, variables, gráficos, entre otros) que se almacenan al ejecutar diferentes análisis.
Panel misceláneo (inferior derecha): Este espacio tiene 5 opciones://
Por defecto, la consola se encuentra en el panel izquierdo. Primero aparece un texto informativo y después el prompt del sistema (“>”). ¿Vemos el cursor intermitente? Aquí es donde R espera que le demos instrucciones. Para ejecutar las instrucciones y obtener el resultado pulsamos Enter.
Trabajar en la Consola es muy limitado ya que en la Consola las instrucciones generalmente se escriben y ejecutan una por una. Lo habitual es trabajar conscripts o ficheros de instrucciones. Estos ficheros tienen la extensión .R. Para crear un script, seleccionamos: File > New File > R Script (en la parte superior izquierda)
Ahora el panel del script se sitúa en la parte superior-izquierda de RStudio y la Consola en el panel inferior-izquierdo. Por defecto, el nombre del nuevo script es “Untitled1”.
El tipo de dato numérico en R esta compuesto por tipos de datos: double (reales) y enteros (numeric) . Se puede comprobar si un objeto es numérico con la función mode o si la función is.numeric devuelve como resultado la palabra TRUE.
Los datos double en R son la representación de un objeto numérico de doble precisión. Tenga en cuenta que, de forma predeterminada, todos los números son double en R y que nf, -Inf, NaN, la notación científica y la notación hexadecimal de números también son doubles.
mode(55) #numeric
## [1] "numeric"
is.numeric(3) #TRUE
## [1] TRUE
Adicionalmente, se pueden usar otras funciones para identificar la variable como numérica, por ejemplo con la función class
prueba <- 34.80
class(prueba) #numeric
## [1] "numeric"
El tipo de dato entero se puede crear agregando una L a un número. Este tipo de datos es útil si se quiere pasar algún objeto de R a una función de C++ o FORTRAN que espera un valor entero, por lo que este tipo de datos generalmente no es necesario. Se puede verificar el tipo de datos con la función is.integer.
y <- 2L
typeof(y) # "integer"
## [1] "integer"
is.integer(3) # FALSE
## [1] FALSE
is.integer(3L) # TRUE
## [1] TRUE
is.integer(y) # TRUE
## [1] TRUE
Los caracteres o las cadenas de caracteres son: símbolos, letras, palabras o frases dentro de comillas dobles o simples. Se puede verificar que algún objeto es de tipo carácter con la función is.character.
letra <- "a"
typeof(letra) # "character"
## [1] "character"
is.character(letra) # TRUE
## [1] TRUE
El tipo logical es la forma que tiene R para caracterizar los datos binarios. Estos datos son normalmente usados en test lógicos y son conocidos como datos booleanos o lógicos y están compuestos por los valores TRUE, FALSE y NA. Nótese que se puede usar T (TRUE) y F (FALSE) como simplificación de las palabras extensas. Sin embargo, esto no se recomienda porque se podría sobrescribir el valor de T o F pero no el de TRUE o FALSE, como se muestra en el siguiente bloque de código.
F # FALSE
## [1] FALSE
a <- T
# Puedes nombrar una variable como T o F
F <- a
F # TRUE
## [1] TRUE
# No puedes nombrar una variable como TRUE o FALSE
a <- TRUE
Otro ejemplo
a <- 2
b <- 4
a == b # ¿es igual a y b?
## [1] FALSE
## [1] FALSE
Una variable factor es una variable categórica. Los vectores de caracteres a menudo se almacenan como factores para explorar funciones. Por ejemplo, esto es usado en análisis de regresión.
vector_mes_malo <- factor(c("enero", "febrero", "marzo", "abril", "enero"))
class(vector_mes_malo)
## [1] "factor"
El tipo de dato complejo es un objeto que incluye un numero imaginario (i), el tipo de dato imaginario tiene una parte real y una parte imaginaria (parte que incluye la (i)). Como los números imaginarios generalmente no se usan en estadística, este tipo de datos no es muy común en las aplicaciones de los cursos aquí referenciados. La función para verificar este tipo de datos es is.complex.
1 + 3i
## [1] 1+3i
typeof(1 + 3i) # "complex"
## [1] "complex"
is.complex(1 + 3i)
## [1] TRUE
Este tipo de datos es el de mayor utilidad en hidrclimatología, pues permite organizar la información de acuerdo a la variable temporal (fechas) reprotada por cada variabe hidroclimatológica. Almacena sus valores internamente como el número de días transcurridos desde el 1 de enero de 1970; para las fechas anteriores el número de días se cuenta en sentido negativo.
R dispone en su paquete base de dos clases específicamente diseñadas para tratar con datos de tipo fecha/hora: Date (solo para fechas) y POSIXt (además de la fecha incluye hora y huso horario); esta última clase contiene dos subclases, POSIXct y POSIXlt que se diferencian simplemente en la forma en que almacenan internamente la fecha y la hora.
Por ejemplo, si se introduce la fecha en otro formato (por ejemplo “dd/mm/yyyy”), hemos de indicarlo al usar as.Date para que R pueda interpretar la fecha correctamente
navidad=as.Date("25/12/2013",format="%d/%m/%Y") #[1] "2013-12-25"
navidad
## [1] "2013-12-25"
En R existen varios tipos de objectos que permiten que el usuario pueda almacenar la información para realizar procedimientos estadísticos y gráficos. Los principales objetos en R son vectores, matrices, arreglos, marcos de datos y listas. A continuación se presentan las características de estos objetos y la forma para crearlos.
Las variables sirven para almacenar un valor que luego vamos a utilizar en algún procedimiento.
Para hacer la asignación de un valor a alguna variable se utiliza el
operador <-
entre el valor y el nombre de la variable. A
continuación un ejemplo sencillo.
x <- 5
2 * x + 3
En el siguiente ejemplo se crea la variable pais
y se
almacena el nombre Colombia, luego se averigua el número de caracteres
de la variable pais
.
pais <- "Colombia"
nchar(pais)
Los vectores vectores son arreglos ordenados en los cuales se puede
almacenar información de tipo numérico (variable cuantitativa),
alfanumérico (variable cualitativa) o lógico (TRUE
o
FALSE
), pero no mezclas de éstos. La función de R para
crear un vector es c()
y que significa concatenar; dentro
de los paréntesis de esta función se ubica la información a almacenar.
Una vez construído el vector se acostumbra a etiquetarlo con un nombre
corto y representativo de la información que almacena, la asignación se
hace por medio del operador <-
entre el nombre y el
vector.
A continuación se presenta un ejemplo de cómo crear tres vectores que contienen las respuestas de cinco personas a tres preguntas que se les realizaron.
edad <- c(15, 19, 13, NA, 20)
deporte <- c(TRUE, TRUE, NA, FALSE, TRUE)
comic_fav <- c(NA, 'Superman', 'Batman', NA, 'Batman')
El vector edad
es un vector cuantitativo y contiene las
edades de las 5 personas. En la cuarta posición del vector se colocó el
símbolo NA
que significa Not Available
debido a que no se registró la edad para esa persona. Al hacer una
asignación se acostumbra a dejar un espacio antes y después del operador
<-
de asignación. El segundo vector es llamado
deporte
y es un vector lógico que almacena las respuestas a
la pregunta de si la persona practica deporte, nuevamente aquí hay un
NA
para la tercera persona. El último vector
comic_fav
contiene la información del cómic favorito de
cada persona, como esta variable es cualitativa es necesario usar las
comillas ' '
para encerrar las respuestas.
Cuando se usa NA
para representar una información
Not Available no se deben usar comillas.
Es posible usar comillas sencillas 'foo'
o comillas
dobles "foo"
para ingresar valores de una variable
cualitativa.
Si se desea ver lo que está almacenado en cada uno de estos vectores, se debe escribir en la consola de R el nombre de uno de los objetos y luego se presiona la tecla enter o intro, al realizar esto lo que se obtiene se muestra a continuación.
edad
deporte
comic_fav
Una variable es un vector de longitud uno.
Para extraer un elemento almacenado dentro un vector se usan los
corchetes []
y dentro de ellos la posición o posiciones que
interesan.
Si queremos extraer la edad de la tercera persona escribimos el
nombre del vector y luego [3]
para indicar la tercera
posición de edad
, a continuación el código.
edad[3]
Si queremos conocer el cómic favorito de la segunda y quinta persona,
escribimos el nombre del vector y luego, dentro de los corchetes,
escribimos otro vector con las posiciones 2 y 5 que nos interesan así
[c(2, 5)]
, a continuación el código.
comic_fav[c(2, 5)]
Si nos interesan las respuestas de la práctica de deporte, excepto la
de la persona 3, usamos [-3]
luego del nombre del vector
para obtener todo, excepto la tercera posición.
deporte[-3]
Si desea extraer varios posiciones de un vector NUNCA escriba esto:
mivector[2, 5, 7]
. Tiene que crear un vector con las
posiciones y luego colocarlo dentro de los corchetes así:
mivector[c(2, 5, 7)]
Las matrices son arreglos rectangulares de filas y columnas con
información numérica, alfanumérica o lógica. Para construir una matriz
se usa la función matrix( )
. Por ejemplo, para crear una
matriz de 4 filas y 5 columnas (de dimensión \(4 \times 5\)) con los primeros 20 números
positivos se escribe el código siguiente en la consola.
mimatriz <- matrix(data=1:20, nrow=4, ncol=5, byrow=FALSE)
El argumento data
de la función sirve para indicar los
datos que se van a almacenar en la matriz, los argumentos
nrow
y ncol
sirven para definir la dimensión
de la matriz y por último el argumento byrow
sirve para
indicar si la información contenida en data
se debe
ingresar por filas o no. Para observar lo que quedó almacenado en el
objeto mimatriz
se escribe en la consola el nombre del
objeto seguido de la tecla enter o
intro.
mimatriz
Al igual que en el caso de los vectores, para extraer elementos
almacenados dentro de una matriz se usan los corchetes
[ , ]
y dentro, separado por una coma, el número de fila(s)
y el número de columna(s) que nos interesan.
Si queremos extraer el valor almacenado en la fila 3 y columna 4 usamos el siguiente código.
mimatriz[3, 4]
Si queremos recuperar toda la fila 2 usamos el siguiente código.
mimatriz[2, ] # No se escribe nada luego de la coma
Si queremos recuperar toda la columna 5 usamos el siguiente código.
mimatriz[, 5] # No se escribe nada antes de la coma
Si queremos recuperar la matriz original sin las columnas 2 y 4 usamos el siguiente código.
mimatriz[, -c(2, 4)] # Las columnas como vector
Si queremos recuperar la matriz original sin la fila 1 ni columna 3 usamos el siguiente código.
mimatriz[-1, -3] # Signo de menos para eliminar
Un arreglo es una matriz de varias dimensiones con información
numérica, alfanumérica o lógica. Para construir una arreglo se usa la
función array( )
. Por ejemplo, para crear un arreglo de
\(3 \times 4 \times 2\) con las
primeras 24 letras minúsculas del alfabeto se escribe el siguiente
código.
miarray <- array(data=letters[1:24], dim=c(3, 4, 2))
El argumento data
de la función sirve para indicar los
datos que se van a almacenar en el arreglo y el argumento
dim
sirve para indicar las dimensiones del arreglo. Para
observar lo que quedó almacenado en el objeto miarray
se
escribe en la consola lo siguiente.
miarray
Para recuperar elementos almacenados en un arreglo se usan también corchetes, y dentro de los corchetes, las coordenadas del objeto de interés.
Si queremos extraer la letra almacenada en la fila 1 y columna 3 de
la segunda capa de miarray
usamos el siguiente código.
miarray[1, 3, 2] # El orden es importante
Si queremos extraer la segunda capa completa usamos el siguiente código.
miarray[,, 2] # No se coloca nada en las primeras posiciones
Si queremos extraer la tercera columna de todas las capas usamos el siguiente código.
miarray[, 3,] # No se coloca nada en las primeras posiciones
El marco de datos marco de datos o data frame es uno de los
objetos más utilizados porque permite agrupar vectores con información
de diferente tipo (numérica, alfanumérica o lógica) en un mismo objeto,
la única restricción es que los vectores deben tener la misma longitud.
Para crear un marco de datos se usa la función
data.frame( )
, como ejemplo vamos a crear un marco de datos
con los vectores edad
, deporte
y
comic_fav
definidos anteriormente.
mimarco <- data.frame(edad, deporte, comic_fav)
Una vez creado el objeto mimarco
podemos ver el objeto
escribiendo su nombre en la consola, a continuación se muestra lo que se
obtiene.
mimarco
De la salida anterior vemos que el marco de datos tiene 3 variables (columnas) cuyos nombres coinciden con los nombres de los vectores creados anteriormente, los números consecutivos al lado izquierdo son sólo de referencia y permiten identificar la información para cada persona en la base de datos.
Para recuperar las variables (columnas) almacenadas en un marco de
datos se puede usar el operador $
, corchetes simples
[]
o corchetes dobles [[]]
. A continuación
algunos ejemplos para entender las diferencias entre estas opciones.
Si queremos extraer la variable deporte
del marco de
datos mimarco
como un vector usamos el siguiente
código.
mimarco$deporte # Se recomienda si el nombre es corto
Otra forma de recuperar la variable deporte
como vector
es indicando el número de la columna donde se encuentra la variable.
mimarco[, 2] # Se recomienda si recordamos su ubicacion
Otra forma de extraer la variable deporte
como vector es
usando [[]]
y dentro el nombre de la variable.
mimarco[["deporte"]]
Si usamos mimarco["deporte"]
el resultado es la variable
deporte
pero en forma de marco de datos, no en forma
vectorial.
mimarco["deporte"]
Si queremos extraer un marco de datos sólo con las variables deporte y edad podemos usar el siguiente código.
mimarco[c("deporte", "edad")]
Por otra, si queremos la edad
de las personas que están
en las posiciones 2 hasta 4 usamos el siguiente código.
mimarco[2:4, 1]
Para extraer partes de un marco de datos se puede utilizar la función
subset(x, subset, select)
. El parámetro x
sirve para indicar el marco de datos original, el parámetro
subset
sirve para colocar la condición y el parámetro
select
sirve para quedarnos sólo con algunas de las
variables del marco de datos. A continuación varios ejemplos de la
función subset
para ver su utilidad.
Si queremos el marco de datos mimarco
sólo con las
personas que SI practican deporte usamos el siguiente código.
subset(mimarco, subset=deporte == TRUE)
Si queremos el marco de datos mimarco
sólo con las
personas mayores o iguales a 17 años usamos el siguiente código.
subset(mimarco, subset=edad >= 17)
Si queremos el submarco con deporte y comic de las personas menores de 20 años usamos el siguiente código.
subset(mimarco, subset=edad < 20, select=c('deporte', 'comic_fav'))
Si queremos el marco de datos mimarco
sólo con las
personas menores de 20 años y que SI practican deporte usamos el
siguiente código.
subset(mimarco, subset=edad < 20 & deporte == TRUE)
Leer la base de datos medidas del cuerpo disponible en este enlace https://raw.githubusercontent.com/fhernanb/datos/master/medidas_cuerpo. Extraer de esta base de datos una sub-base o subconjunto que contenga sólo la edad, peso, altura y sexo de aquellos que miden más de 185 cm y pesan más de 80 kg.
url <- 'https://raw.githubusercontent.com/fhernanb/datos/master/medidas_cuerpo'
dt1 <- read.table(url, header=T)
dim(dt1) # Para conocer la dimensión de la base original
dt2 <- subset(x=dt1, subset=altura > 185 & peso > 80,
select=c('sexo', 'edad', 'peso', 'altura'))
dt2 # Para mostrar la base de datos final
Al almacenar la nueva base de datos en el objeto dt2
se
puede manipular este nuevo objeto para realizar los análisis de
interés.
Las listas son otro tipo de objeto muy usado para almacenar objetos
de diferente tipo. La instrucción para crear una lista es
list( )
. A continuación vamos a crear una lista que
contiene tres objetos: un vector con 5 números aleatorios llamado
mivector
, una matriz de dimensión \(6 \times 2\) con los primeros doce números
enteros positivos llamada matriz2
y el tercer objeto será
el marco de datos mimarco
creado en el apartado anterior.
Las instrucciones para crear la lista requerida se muestran a
continuación.
set.seed(12345)
mivector <- runif(n=5)
matriz2 <- matrix(data=1:12, ncol=6)
milista <- list(E1=mivector, E2=matriz2, E3=mimarco)
La función set.seed
de la línea número 1 sirve para
fijar la semilla de tal manera que los números aleatorios generados en
la segunda línea con la función runif
sean siempre los
mismos. En la última línea del código anterior se construye la lista,
dentro de la función list
se colocan los tres objetos
mivector
, matriz2
y mimarco
. Es
posible colocarle un nombre especial a cada uno de los elementos de la
lista, en este ejemplo se colocaron los nombres E1
,
E2
y E3
para cada uno de los tres elementos.
Para observar lo que quedó almacenado en la lista se escribe
milista
en la consola y el resultado se muestra a
continuación.
milista
Para recuperar los elementos almacenadas en una lista se usa el
operador $
, corchetes dobles [[]]
o corchetes
sencillos []
. A continuación unos ejemplos para entender
cómo extraer elementos de una lista.
Si queremos la matriz almacenada con el nombre de E2
dentro del objeto milista
se puede usar el siguiente
código.
milista$E2
Es posible indicar la posición del objeto en lugar del nombre, para eso se usan los corchetes dobles.
milista[[2]]
El resultado obtenido con milista$E2
y
milista[[2]]
es exactamente el mismo.
Vamos ahora a solicitar la posición 2 pero usando corchetes
sencillos.
milista[2]
La apariencia de este último resultado es similar, no igual, al
encontrado al usar $
y [[]]
. Para ver la
diferencia vamos a pedir la clase a la que pertenecen los tres últimos
objetos usando la función class
. A continuación el código
usado.
class(milista$E2)
class(milista[[2]])
class(milista[2])
De lo anterior se observa claramente que cuando usamos $
o [[]]
el resultado es el objeto almacenado, una matriz.
Cuando usamos []
el resultado es una lista
cuyo contenido es el objeto almacendado.
Al manipular listas con $
y [[]]
se
obtienen los objetos ahí almacenados, al manipular listas con
[]
se obtiene una lista.
Usando R como una calculadora
1 + 100
R te mostrará la respuesta, precedido de un “[1]”. No te preocupes por esto por ahora, lo explicaremos más adelante. Por ahora piensa en eso como parte de la salida.
Al igual que bash, si escribes un comando incompleto R esperará a que lo completes:
“1 +”
Si usas R desde la línea de comandos en lugar de estar dentro de RStudio, debes usar Ctrl + C en lugar de Esc para cancelar el comando. ¡Esto se aplica también a los usuarios de Mac!
La cancelación de un comando no sólo es útil para matar comandos incompletos: también puedes usarlo para decirle a R que deje de ejecutar el código (por ejemplo, si tarda mucho más de lo que esperabas), o para deshacerte del código que estás escribiendo actualmente.
Los operadores aritméticos de R nos permiten realizar operaciones matemáticas, como sumas, divisiones o multiplicaciones, entre otras. La siguiente tabla resume todos los operadores aritméticos de R base.
# Operaciones básicas
3 + 5
8 - 3
7 * 5
1/2
4 ^ 4
4 ** 4
5 %% 3
5 %/% 3
Los operadores de comparación o relacionales están diseñados para comparar objetos. El resultado de estas comparaciones son de tipo booleano. La siguiente tabla resume los operadores relacionales de R.
Puedes comparar valores enteros con estos operadores de la siguiente manera.
# Operaciones básicas
3 > 5
3 < 5
3 >= 5
3 <= 5
3 == 5
3 != 5
Los operadores booleanos o lógicos en R se utilizan para especificar múltiples condiciones entre objetos. Estas comparaciones devuelven valores TRUE o FALSE.
# Operaciones básicas
40 & 5 > 30
40 | 5 > 30
# Vectores
x <- c(3, 4, 5)
y <- c(3, 5, 1)
x & y
x | y
!x
Otras
funciones básicas muy utilizadas en estadística son: sin, cos, tan,
asin, acos, atan, atan2, log, logb, log10, exp, sqrt, abs. A
continuación algunos ejemplos de las anteriores funciones.
# Ejemplos de medidas trigonométricas
angulos <- c(0, pi/2, pi)
sin(angulos)
tan(angulos)
# Ejemplos de logaritmos
log(100)
logb(125, base=5)
# Ejemplos de exponencial
exp(1)
exp(2)
exp(1:3)
# Ejemplos de raices
sqrt(49) # Raiz cuadrada de 49
27 ^ (1/3) # Raiz cúbica de 273
#Ejemplos de valor absoluto
abs(2.5)
abs(-3.6)
Use funciones o procedimientos (varias líneas) de R para responder cada una de las siguientes preguntas.
Construya un vector con la primeras 20 letras MAYÚSCULAS del abecedario usando la función LETTERS. Explique qué es una función y cómo trabaja la función LETTERS.
Construya una matriz de \(10 \times 10\) con los primeros 100 números positivos pares. Explique paso a paso qué hace cada línea de código
Construya una matriz identidad de dimension \(3 \times 3\). Recuerde que una matriz identidad tiene sólo unos en la diagonal principal y los demás elementos son cero.
Construya una lista con los anteriores tres objetos creados.
Realice una encuesta a sus compañeros de clase con las siguientes preguntas:
Construya un vector por cada ítem y luego agrúpelos en un data frame y extraiga la siguente información:
consolide las respuestas en un data frame y asigne a cada persona un ID o nickname. Luego con la función filter, cree un código que permita ver las películas mejor valoradas por usuario y un alista de las mejores 5 películas recomendadas por todos sus compañeros.