Como crear tu primer paquete con datos y algunas funciones.
Para crear un paquete principalmente hay que saber crear funciones.
Pero ¿Porque crear un paquete? 🤔
Algunas razones:
Para crear paquetes se puede usar el paquete usethis
Antes de iniciar a crear un paquete, se puede consultar si el nombre no esta siendo usando en otro paquete en la página CRAN. También existe el paquete available para revisar si el paquete ya existe en CRAN o en github y si el nombre del paquete puede ser ofensivo.
install.packages('available')
library(available)
available("nombre_paquete")
Te va preguntar si quieres que revise por contenido ofensivo, puedes poner Y.
Urban Dictionary can contain potentially offensive results,/ [N]o: should they be included? [Y]es
Después abre paginas para mostrar que significa el nombre de el paquete.
Para crear un paquete la función create_package crea
el esqueleto de los paquetes.
Dentro puedes poner
el nombre del paquete que te interesa crear.
usethis::create_package("nombre_paquete")
Aparecerá algo así:
'nombre_paquete/'
√ Creating '...'
√ Setting active project to 'R/'
√ Creating 'DESCRIPTION'
√ Writing : nombre_paquete
Package: What the Package Does (One Line, Title Case)
Title: 0.0.0.9000
Version@R (parsed):
Authors* First Last <first.last@example.com> [aut, cre] (YOUR-ORCID-ID)
: What the package does (one paragraph).
Description: `use_mit_license()`, `use_gpl3_license()` or friends to
License
pick a license: UTF-8
Encoding: true
LazyData: list(markdown = TRUE)
Roxygen: 7.1.1
RoxygenNote'NAMESPACE'
√ Writing 'nombre_paquete.Rproj'
√ Writing '^nombre_paquete\\.Rproj$' to '.Rbuildignore'
√ Adding '.Rproj.user' to '.gitignore'
√ Adding '^\\.Rproj\\.user$' to '.Rbuildignore'
√ Adding '...' in new RStudio session
√ Opening '<no active project>' √ Setting active project to
Nota: Si te encuentras dentro de un proyecto va a preguntar si deseas sobregrabar el proyecto existente. Si es el caso: 2: Absolutely
'NAMESPACE'
v Writing -existing file 'nombre_paquete.Rproj'?
Overwrite pre
1: Not now
2: Absolutely
3: No way
Aparecerá algo como:
'nombre_paquete.Rproj'
v Writing '^nombre_paquete\\.Rproj$' to '.Rbuildignore'
v Adding '^\\.Rproj\\.user$' to '.Rbuildignore'
v Adding '...' in new RStudio session
v Opening '<no active project>' v Setting active project to
Se abrirá el proyecto en otra ventana.
La función anterior creó los archivos:
- .gitignore
- .Rbuildignore
- DESCRIPTION
- NAMESPACE
- README.md
Las Carpetas:
- R
Si ya tienes instalado git puedes directamente conectar el paquete con tu repositorio, escribiendo en tu consola:
usethis::use_git()
Aparecerá algo como:
'...'
√ Setting active project to '.Rdata', '.httr-oauth', '.DS_Store' to '.gitignore'
√ Adding 6 uncommitted files:
There are '.gitignore'
'.Rbuildignore'
'DESCRIPTION'
'NAMESPACE'
Is it ok to commit them?
1: Absolutely not
2: Yup
3: Negative
3: Yup… es si
Aparecerá algo como:
√ Adding files'Initial commit
√ Making a commit with message A restart of RStudio is required to activate the Git pane
Restart now?
1: Yup
2: No
3: Not now
Si deseas reiniciar RStudio para activar git:
1: Yup… es sip
Se reiniciara la sesión
Para ahora conectarlo con github, hay que escribir en la consola:
usethis::use_github()
Aparecerá algo como:
i Defaulting to https Git protocol'C:/...'
√ Setting active project to branch ('master')
√ Checking that current branch is default '...'
√ Creating GitHub repository 'origin' to 'https://github.com/...git'
√ Setting remote in DESCRIPTION to 'https://github.com/...'
√ Setting URL field in DESCRIPTION to 'https://github.com/...'
√ Setting BugReports field 1 uncommitted file:
There is 'DESCRIPTION'
Is it ok to commit it?1: No
2: No way
3: I agree
Si es correcto elegir 3: I agree, que significa de acuerdo
Aparecerá algo como:
√ Adding files'Add GitHub links to DESCRIPTION'
√ Making a commit with message 'master' branch to GitHub and setting 'origin/master' as upstream branch
√ Pushing 'https://github.com/...' √ Opening URL
Abrirá github
Escribir en la consola
devtools::check()
Esta función revisa la versión, plataforma, sesiones y demás.
Tarda un poquito.
0 errors √ | 1 warning x | 0 notes √
El warning ocurre porque hay que darle una licencia al paquete.
-standard license specification:
Non`use_mit_license()`, `use_gpl3_license()` or friends to pick a
license: FALSE Standardizable
Para software la licencia más común es MIT
usethis::use_mit_license("Mi Nombre")
Aparecerá algo como:
in DESCRIPTION to 'MIT + file LICENSE'
√ Setting License field 'LICENSE'
√ Writing 'LICENSE.md'
√ Writing '^LICENSE\\.md$' to '.Rbuildignore' √ Adding
Para revisar si funcionó:
devtools::check()
Tarda un poquito.
0 errors √ | 0 warning √ | 0 notes √
Para agregar metadata se debe abrir y modificar el documento que dice DESCRIPTION, agregando tus datos.
Esta es la información de contacto si hay problemas con el paquete.
Para crear un nuevo README, el paquete usethis tiene una función para crearlo de manera automática,
library(usethis)
use_readme_rmd(open = rlang::is_interactive())
'...'
√ Setting active project to 'README.Rmd'
√ Writing '^README\\.Rmd$' to '.Rbuildignore'
√ Adding 'README.Rmd'
Modify '.git/hooks/pre-commit' √ Writing
Para agregar datos en tu paquete, puedes cargar tus datos y después
guardarlos dentro de tu proyecto.
Por convención los datos son colocados en una carpeta que lleve el
nombre de data dentro del paquete.
Puedes crear
esta carpeta desde RStudio abriendo la pestaña de Files
y eligiendo New Folder.
Para comprimir datos pesados puedes guardarlos como .rda.
save(TDR_raw, file="TDR_raw.rda")
Para revisar el peso de los datos puedes usar:
object.size(TDR_raw)
pryr::mem_used()
Para documentar tus datos, puedes abrir un nuevo script (File>NewFile>R Script) o usar la función del paquete usethis.
Tanto la función use_r como use_data funcionan.
Esta función agrega comentarios Roxigen y guarda el documento en tu
folder llamado R.
En mi caso yo le di al script el
mismo nombre que a los datos.
#' Mis datos son datos de...
#' Contiene 264197 obs de 1 variable.
#' @docType data
#' @usage data(mis_datos)
#' @format Un data frame con 1 variable
#' @keywords datasets
#' @references Lerma et al. 2021
#' @examples
#' data(mis_datos)
"mis_datos"
Una vez creado el archivo .rda y .R se puede revisar si funcionó usando funciones del paquete devtools
devtools::check()
Si los datos son muy pesados y te aparece un mensaje como este:
: significantly better compression could be obtained
Note--resave-data by using R CMD build
Es mejor agregar el argumento compress.
save(TDR_raw, file="TDR_raw.rda", compress = "xz")
Agrega datos al paquete
Si después de usar devtools::check(), aparece:
0 errors √ | 0 warnings √ | 0 notes √
Ya tienes tu primer paquete con datos 🥳.
devtools::install("C:/....")
devtools::install_github("Desarrollador/paquete")
RData
Si aparece el mensaje WARNING: Added dependency on R >= 3.5.0
because serialized objects in serialize/load version 3 cannot be read in
older versions of R. Hay que usar .RData
save(TDR_raw, file = "TDR_raw.RData", version = 2)
LazyData Tambien tener cuidado de incluir en DESCRIPTION
LazyData: true
If LazyData DB of 21.3 MB without LazyData Compression set
AgregarLazyDataCompression:xz
If checking data for ASCII and uncompressed saves … Warning: package needs dependence on R (>= 2.10)
In DESCRIPTION:: R (>= 2.10) Depends
Para poder usar directamente los datos
Para este paso deberías tener alguna función en mente.
Si aún no sabes como crear tu primera función puedes ir a r4ds.
La estructura es algo así:
nombre_de_la_funcion<-function(argumentos){
algo_que_haga_la_funcion_usando(argumentos)
return(resultado)
}
Para agregar la función al paquete.
usethis::use_r("mi_primera_funcion")
Abre un nuevo script
Pega allí la función
Aparecerá algo como:
'C:/...'
√ Setting active project to 'R/mi_primera_funcion.R'
Modify `use_test()` to create a matching test file Call
Ahora en la carpeta R aparecerá dentro la función
Agregar un Roxigen skeleton:
- Poner el cursor justo en la
primera linea de la función.
- Abrir la pestaña de Code>Insert
Reoxygen Skeleton (también funciona con Control+Alt+Shift+R).
Aparecerá algo como:
#' Title
#'
#' @param data
#' @param trip_start
#' @param trip_end
#'
#' @return
#' @export
#'
#' @examples
Después de rellenar la información necesaria, para agregar la función al paquete, escribe en la consola:
devtools::document()
Aparecerá algo como:
Writing NAMESPACE Writing mi_primera_funcion.Rd
Al abrir la carpeta man aparecerá un documento
rellenado.
El nombre man viene de manual y esta es la
documentación del paquete.
No debe ser editado de manera manual.
Ya puedes revisar la documentación.
?mi_primera_funcion
devtools::check()
Te recomiendo probar tu función con datos de ejemplo, antes de incluirla en el paquete.
data=misdatos
mi_primer_argumento='mi_primer_argumento'
mi_segundo_argumento='mi_segundo_argumento'
mi_funcion(data = mis_datos,
mi_primer_argumento='mi_primer_argumento',
mi_segundo_argumento='mi_segundo_argumento')
Otra opción es usar el paquete ‘testthat’ para probar tu función.
Para agregar la función al paquete:
usethis::use_r("tu_funcion")
Abre un nuevo script. Pega allí la función. En la consola aparecerá algo como:
'R/tu_funcion.R'
Modify `use_test()` to create a matching test file Call
Ahora en la carpeta R dentro del paquete aparece la
función.
Nota sugiere que uses use_test pero puede en conflicto
con el siguiente paso.
Puedes usar /rm() para quitar tu función.
Para poner la función en la memoria local y confirmar que se ejecute hay que incluirla en el paquete y probarla.
devtools::load_all()
Para documentar la función hay que crear un Roxigen skeleton.
Para esto se debe poner el cursor justo en la primera linea de la
función.
Después ir a la pestaña de Code>Insert Reoxygen Skeleton (tambíen
funciona con Control+Alt+Shift+R).
Va a aparecer algo así:
#' Title
#'
#' @param data
#' @param mi_primer_argumento
#' @param mi_segundo_argumento
#'
#' @return
#' @export
#'
#' @examples
Nota que identifica de manera automática las variables de la función
Ahora que ya esta la función y la documentación para agregar el paquete hay que escribir en la consola:
devtools::document()
Aparece:
Writing NAMESPACE Writing mi_funcion.Rd
Ahora en la carpeta man, aparece un documento
rellenado.
man viene de manual y esta es la documentación del
paquete.
Nota No debe ser editado de manera manual.
Puedes revisar la documentación de la función.
?mi_funcion
Dependencias son paquetes necesarios para que la función, funcione.
Para revisar si necesitas dependencias se puede usar:
devtools::check()
Si tu paquete tiene dependencias, aparecerán errores, warnings y notas.
Por ejemplo, un paquete que usa: - un %>% (pipe) depende del paquete magrittr, y - la función separate depende del paquete dplyr.
Para agregar las dependencias se puede escribir el nombre de los paquetes dentro de la función use_package
usethis::use_package("dplyr")
Aparecerá algo como:
'dplyr' to Imports field in DESCRIPTION
√ Adding `dplyr::fun()` Refer to functions with
Así mismo aparecerá en el documento DESCRIPTION:
Imports:
dplyr
Lo siguiente es especificar el paquete en la función, tal como recomienda el siguiente mensaje.
`dplyr::fun()` Refer to functions with
La función pipe (%>%) del paquete magrittr es especial.
Por lo que hay que usar:
usethis::use_pipe()
Aparecerá algo como:
'magrittr' to Imports field in DESCRIPTION
√ Adding 'R/utils-pipe.R'
√ Writing `devtools::document()` to update 'NAMESPACE' Run
Se recomienda volver a documentar.
devtools::document()
Ahora deberá aparecer en la carpeta R un script llamado
utils-pipe.R y
en el archivo DESCRIPTION deberá aparecer Imports
magrittr
Para checar el paquete:
devtools::check()
0 errors √ | 0 warnings √ | 0 notes √
Listo! el paquete esta completo 🥳
Cuando queremos agregar alguna función que incluya cálculos de desviación estándar, aunque no se necesite cargar el paquete en RStudio, la función proviene de un paquete.
El paquete es stats
Por lo tanto el paquete stats debe ser incluido en las dependencias.
usethis::use_package("stats")
Y agregado a la función.
devtools::check()
0 errors √ | 0 warnings √ | 0 notes √
Listo! el paquete esta completo 🥳
Cuando creamos una función con ggplot hay que declarar el uso de la función en varios argumentos de la función. Aquí puedes leer más.
Si no, aparecerá un error:
1 error x | 0 warnings √ | 1 note x
Esto occurre debido a que al revisar el paquete, no detecta varias funciones del paquete ggplot.
function definition for 'aes' no visible global
Ejemplo:
ggplot2::ggplot(data=data,ggplot2::aes(x=.data[[var1]],
y=as.numeric(.data[[var2]])))+
ggplot2::geom_line()+
ggplot2::ylab("Diving depth (m)")+
ggplot2::xlab("Month.Day Hour:Minute")+
ggplot2::scale_y_reverse()+
ggplot2::theme_bw()
for possible problems ... checking R code
También pueden aparecer problemas con las variables al usar ggplot dentro de una función.
for global variable '.data' no visible binding
Para resolver esto hay que declarar las variables dentro de la función y posteriormente usar .data
<-TDR_trip
data<-time_column
var1<-depth_column
var2
::ggplot(data,
ggplot2::aes(x=.data[[var1]],
ggplot2y=.data[[var2]))+
::geom_line() ggplot2
devtools::check()
0 errors √ | 0 warnings √ | 0 notes √
Listo! el paquete esta completo 🥳
Problema En algunas funciones puedes haber usado
assign. Usar assign no es recomendado, por lo que aparecerá una nota.
Solución Usar return().
Problema No nested functions, no circular
dependencies.
Solución No puedes usar funciones de
tu paquete en otras funciones del mismo paquete.
Problema Borrar funciones.
Solución Para borrar funciones se debe borrar el script
en el archivo R y volver a documentar el paquete para que se reflejen
los cambios.
Problema El ejemplo tiene más de 100 caracteres, es
considerado muy largo.
Solución Separar en la
documentación.
100 characters: \examples lines wider than
Problema Solo puedo tener un resultado (return)
Solución Crea una lista con los returns.
Por
ejemplo:
funcion(primer_argumento, segundo_argumento){
<-primer_argumento*segundo_argumento
multiplicacion<-primer_argumento+segundo_argumento
suma<-(list("multiplicacion"=multiplicacion,"suma"=suma))
listareturn(lista)
}
Problema Al usar slot en sapply.
Solución Hay que agregar la dependencia
methods.
usethis::use_r("nombre_funcion")
#Insertar Roxigen Skeleton (CTRL+ALT+SHIFT+R)
devtools::document()
devtools::check()
usethis::use_package("ggplot2")
#Referirse a funciones con ::
devtools::check()
Es útil agregar warnings para que el usuario (quien sera a veces tu mismo) pueda corregir errores.
Para checar que el data frame contenga datos, revisa que el numero de filas no sea cero.
También puedes revisar si tu data frame contiene una columna de acuerdo a su nombre
Ademas podemos revisar si una columna en especifico aparece en el data frame
️
Para crear un hexSticker puedes usar plantillas:
- En powerpoint
plantilla hecha por
Emi Tanaka
- En R paquete hexSticker
hecho por GuangchuangYu
Para instalar el paquete hexSticker, puedes descargarlo desde en CRAN:
install.packages("hexSticker")
Zenodo es un repositorio de acceso abierto operado por CERN (Organización Europea para la Investigación Nuclear).
Ventajas Permite que se depositen allí artículos de investigación, datos, software, informes y otro tipo de objeto digital relacionado con la investigación. La ventaja frente a github es que asigna un DOI.
Desventajas Las versiones de paquetes se pueden registrar en zenodo. No obstante, NO es tan practico ya que cada versión tiene su propio DOI y la versión anterior no puede ser eliminada.
Libros
R Packages
R Packages 2e
Tutoriales sobre datos
Incluir datos
Documentar datos
Tu paquete en una hora
Piping hot data
Videos
Rladies como crear funciones
Rladies como crear paquetes