3. Nuestra primera función

⏱ Enseñanza: 10 minutos · Ejercicios: 15 minutos

Preguntas

  • ¿Dónde van las funciones de un paquete?
  • ¿Cómo pruebo una función mientras la escribo?

Objetivos

  • Crear un archivo para una función con usethis::use_r().
  • Cargar el paquete en desarrollo con devtools::load_all().
  • Usar el ciclo editar, cargar, probar.

Un archivo para la función

Las funciones de un paquete deben estar en la carpeta R/. Podríamos crear el archivo a mano, pero usethis tiene una función para hacerlo:

💻 En vivo

usethis::use_r("dicho_al_azar")

Si el archivo no existe, lo crea y lo abre. Si ya existe, solo lo abre. Es una forma rápida de ir a la función que queremos editar.

Tip¿Una función por archivo?

No es obligatorio. Hay paquetes que agrupan en un archivo las funciones relacionadas y el nombre del archivo indica qué contiene. Cuando una función es importante (o es larga), conviene que tenga su propio archivo con su mismo nombre.

La primera versión

Empezamos simple, como en cualquier función: unos dichos guardados en un vector, y elegimos uno al azar.

💻 En vivo, en R/dicho_al_azar.R

dicho_al_azar <- function() {
  dichos <- c(
    "Estar al horno",
    "Como perro en cancha de bochas",
    "Pasarlo chancho"
  )
  sample(dichos, size = 1)
}

Analicemos las partes de una función:

  • dicho_al_azar es el nombre de la función
  • function() es la funcion de R que crea funciones.
  • lo que esta entre {} es el cuerpo de la función.

Este es el formato mínimo de una función, ya veremos como ir agregandole mas partes.

Guardamos el archivo y probamos en la consola:

dicho_al_azar()
#> Error in dicho_al_azar() : could not find function "dicho_al_azar"

¡R no la conoce! La función está en un archivo, pero R todavía no la leyó.

load_all(): cargar el paquete en desarrollo

devtools::load_all() carga todo el paquete, como si lo hubiéramos instalado y hecho library():

💻 En vivo

devtools::load_all()
#> ℹ Loading dichosos

dicho_al_azar()
#> [1] "Pasarlo chancho"

Atajo de teclado: Ctrl + Shift + L (en Mac, Cmd + Shift + L).

El ciclo: editar, cargar, probar

Desarrollar un paquete es dar vueltas a este ciclo, muchas veces:

Ciclo de desarrollo: editar el código, cargar con load_all, probar en la consola, y volver a editar Editarel archivo en R/ Cargarload_all() Probaren la consola ¿No anda como esperabas? Otra vuelta.

Una vez que encontramos una versión que nos gusta, corremos devtools::check() cada tanto para ver si rompimos algo.

Nota¿Y si uso Positron?

Todo el código es igual. En Positron, load_all() también tiene el atajo Ctrl/Cmd + Shift + L.

Desafío 3.1: Tu primera función en un paquete 8 minutos

  1. Creá el archivo de la función con usethis::use_r("dicho_al_azar").
  2. Escribí la función dicho_al_azar() (podés copiarla de los snippets).
  3. Agregá al vector un dicho de tu país o de algún otro lado pero que te guste.
  4. Guardá, cargá el paquete con devtools::load_all() y llamá a la función varias veces.
usethis::use_r("dicho_al_azar")

En R/dicho_al_azar.R:

dicho_al_azar <- function() {
  dichos <- c(
    "Estar al horno",
    "Perdido como perro en cancha de bochas",
    "Pasarlo chancho",
    "Un dicho tuyo"          # <- ¡el tuyo!
  )
  sample(dichos, size = 1)
}

En la consola:

devtools::load_all()
dicho_al_azar()
dicho_al_azar()

Desafío 3.2: Poné los pasos en orden 3 minutos

Estos son los pasos para agregar una función nueva a un paquete, pero están desordenados. Ordenalos.

  • devtools::load_all()
  • Escribir la función en el archivo.
  • usethis::use_r("nombre_funcion")
  • Probar la función en la consola.
  • Guardar el archivo.
  1. usethis::use_r("nombre_funcion")
  2. Escribir la función en el archivo.
  3. Guardar el archivo.
  4. devtools::load_all()
  5. Probar la función en la consola.

Y si algo no anda: volver al paso 2. ¡Es un ciclo!

Desafío 3.3: ¿Qué va a pasar? 4 minutos

Agregá otro dicho al vector y guardá el archivo, pero no corras load_all(). Antes de llamar a dicho_al_azar() muchas veces, pensá: ¿va a aparecer el dicho nuevo?

Probalo. Después corré load_all() y volvé a probar.

Sin load_all(), R sigue usando la versión de la función que cargó la última vez: el dicho nuevo no aparece nunca. Guardar el archivo no alcanza; hay que volver a cargar el paquete. Este es uno de los errores más comunes cuando empezamos a desarrollar paquetes: “¡cambié el código y no pasa nada!”.

Puntos clave

  • Las funciones del paquete van en la carpeta R/; usethis::use_r() crea y abre el archivo.
  • devtools::load_all() carga todo el paquete en desarrollo.
  • Guardar no alcanza: después de cada cambio, hay que volver a cargar.
  • Desarrollar es un trabajar en el ciclo: editar, cargar, probar.