EDIT: Hadley Wickham souligne que j'ai mal parlé. R La vérification CMD lance des NOTES, pas des avertissements. Je suis vraiment désolé pour la confusion. C'était ma surveillance.
R CMD check
Lance cette note à chaque fois que j'utilise syntaxe de création de tracé sensée dans ggplot2:
no visible binding for global variable [variable name]
Je comprends pourquoi R CMD check fait cela, mais cela semble criminaliser toute une veine de syntaxe autrement sensée. Je ne sais pas quelles mesures prendre pour que mon colis passe R CMD check
Et soit admis au CRAN.
Sascha Epskamp a précédemment posté sur essentiellement le même problème . La différence, je pense, est que la page de manuel de subset()
dit qu'elle est conçue pour une utilisation interactive .
Dans mon cas, le problème n'est pas sur subset()
mais sur une fonctionnalité centrale de ggplot2
: L'argument data =
.
Voici ne sous-fonction dans mon package qui ajoute des points à un tracé:
JitteredResponsesByContrast <- function (data) {
return(
geom_point(
aes(
x = x.values,
y = y.values
),
data = data,
position = position_jitter(height = 0, width = GetDegreeOfJitter(jj))
)
)
}
R CMD check
, En analysant ce code, dira
granovagg.contr : JitteredResponsesByContrast: no visible binding for
global variable 'x.values'
granovagg.contr : JitteredResponsesByContrast: no visible binding for
global variable 'y.values'
La vérification est techniquement correcte. x.values
Et y.values
JitteredResponsesByContrast()
x.values <- [something]
, Globalement ou dans l'appelant.Au lieu de cela, ce sont des variables dans une trame de données qui sont définies plus tôt et transmises à la fonction JitteredResponsesByContrast()
.
ggplot2 semble encourager l'utilisation d'un argument data
. L'argument data, probablement, est la raison pour laquelle ce code s'exécutera
library(ggplot2)
p <- ggplot(aes(x = hwy, y = cty), data = mpg)
p + geom_point()
mais ce code produira une erreur d'objet introuvable:
library(ggplot2)
hwy # a variable in the mpg dataset
Matthew Dowle recommande régler d'abord les variables problématiques sur NULL, ce qui dans mon cas ressemblerait à ceci:
JitteredResponsesByContrast <- function (data) {
x.values <- y.values <- NULL # Setting the variables to NULL first
return(
geom_point(
aes(
x = x.values,
y = y.values
),
data = data,
position = position_jitter(height = 0, width = GetDegreeOfJitter(jj))
)
)
}
J'apprécie cette solution, mais je ne l'aime pas pour trois raisons.
R CMD check
.aes()
verra nos variables maintenant NULL (ce ne sera pas le cas), tout en obscurcissant le véritable objectif (en rendant R CMD check conscient des variables qu'il ne connaîtrait pas autrement étaient liées) )Vous pouvez utiliser with()
pour signaler explicitement que les variables en question peuvent être trouvées dans un environnement plus vaste. Dans mon cas, l'utilisation de with()
ressemble à ceci:
JitteredResponsesByContrast <- function (data) {
with(data, {
geom_point(
aes(
x = x.values,
y = y.values
),
data = data,
position = position_jitter(height = 0, width = GetDegreeOfJitter(jj))
)
}
)
}
Cette solution fonctionne. Mais, je n'aime pas cette solution car elle ne fonctionne même pas comme je m'y attendais. Si with()
résolvait vraiment le problème du pointage de l'interpréteur vers où se trouvent les variables, alors je ne devrais même pas need l'argument data =
. Mais, with()
ne fonctionne pas de cette façon:
library(ggplot2)
p <- ggplot()
p <- p + with(mpg, geom_point(aes(x = hwy, y = cty)))
p # will generate an error saying `hwy` is not found
Donc, encore une fois, je pense que cette solution a des défauts similaires à la stratégie NULLing:
with()
with()
est trompeur. J'ai encore besoin de fournir un argument data =
; tout ce que with()
fait est d'apaiser R CMD check
.À mon avis, je pourrais choisir trois options:
with()
)Aucun des trois ne me rend heureux et je me demande ce que les gens suggèrent que je (et les autres développeurs de packages souhaitant puiser dans ggplot2) devraient faire. Merci à tous d'avance. J'apprécie vraiment que vous ayez lu ceci :-)
Avez-vous essayé avec aes_string
au lieu de aes
? Cela devrait fonctionner, même si je ne l'ai pas essayé:
aes_string(x = 'x.values', y = 'y.values')
Vous avez deux solutions:
Réécrivez votre code pour éviter une évaluation non standard. Pour ggplot2, cela signifie utiliser aes_string()
au lieu de aes()
(comme décrit par Harlan)
Ajoutez un appel à globalVariables(c("x.values", "y.values"))
quelque part dans le niveau supérieur de votre package.
Vous devez vous efforcer d'obtenir 0 NOTES dans votre colis lors de la soumission à CRAN, même si vous devez faire quelque chose de légèrement hacky. Cela rend la vie plus facile pour CRAN, et plus facile pour vous.
(Mis à jour le 2014-12-31 pour refléter mes dernières réflexions à ce sujet)
Cette question a été posée et répondue il y a un certain temps mais juste pour votre information, puisque version 2.1. il existe un autre moyen de contourner les notes: aes_(x=~x.values,y=~y.values).
Si
getRversion() >= "3.1.0"
Vous pouvez ajouter un appel au niveau supérieur du package:
utils::suppressForeignCheck(c("x.values", "y.values"))
de:
help("suppressForeignCheck")
En 2019, la meilleure façon de contourner cela est d'utiliser le .data
préfixe du package rlang
. Cela indique à R de traiter x.values
et y.values
sous forme de colonnes dans un data.frame
(donc il ne se plaindra pas des variables non définies).
Remarque: Cela fonctionne mieux si vous avez des noms de colonnes prédéfinis dont vous savez qu'ils existeront dans votre entrée de données
#' @importFrom rlang .data
my_func <- function(data) {
ggplot(data, aes(x = .data$x, y = .data$y))
}