EDYCJA: Hadley Wickham zwraca uwagę, że popełniłem błąd. R Kontrola CMD rzuca UWAGI, a nie Ostrzeżenia. Bardzo mi przykro z powodu zamieszania. To był mój niedopatrzenie.
Krótka wersja
R CMD check
rzuca tę notatkę za każdym razem, gdy używam rozsądnej składni tworzenia fabuły w ggplot2:
no visible binding for global variable [variable name]
Rozumiem, dlaczego R CMD to robi, ale wydaje się, że kryminalizacja całej żyły skądinąd sensownej składni. Nie jestem pewien, jakie kroki podjąć, aby moja paczka została przekazana R CMD check
i przyjęta do CRAN.
Tło
Sascha Epskamp poprzednio pisał na zasadniczo ten sam problem . Myślę, że różnica polega na tym, że subset()
strona ta mówi, że została zaprojektowana do użytku interaktywnego .
W moim przypadku kwestia ta nie jest zakończona, subset()
ale dotyczy podstawowej cechy ggplot2
: data =
argumentu.
Przykład kodu, który piszę, który generuje te notatki
Oto podfunkcja w moim pakiecie, która dodaje punkty do wykresu:
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
, podczas analizowania tego kodu, powie
granovagg.contr : JitteredResponsesByContrast: no visible binding for
global variable 'x.values'
granovagg.contr : JitteredResponsesByContrast: no visible binding for
global variable 'y.values'
Dlaczego sprawdzenie R CMD jest prawidłowe
Sprawdzenie jest technicznie prawidłowe. x.values
iy.values
- Nie są zdefiniowane lokalnie w funkcji
JitteredResponsesByContrast()
- Nie są wstępnie zdefiniowane
x.values <- [something]
ani w formie globalnej, ani w dzwoniącym.
Zamiast tego są zmiennymi w ramce danych, która została wcześniej zdefiniowana i przekazana do funkcji JitteredResponsesByContrast()
.
Dlaczego ggplot2 utrudnia złagodzenie kontroli R CMD
ggplot2 wydaje się zachęcać do użycia data
argumentu. Argument data prawdopodobnie przypuszczalnie powoduje wykonanie tego kodu
library(ggplot2)
p <- ggplot(aes(x = hwy, y = cty), data = mpg)
p + geom_point()
ale ten kod wygeneruje błąd „nie znaleziono obiektu”:
library(ggplot2)
hwy # a variable in the mpg dataset
Dwa obejścia i dlaczego nie jestem zadowolony z żadnego
Strategia NULLing out
Matthew Dowle zaleca najpierw ustawienie problematycznych zmiennych na NULL, co w moim przypadku wyglądałoby tak:
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))
)
)
}
Doceniam to rozwiązanie, ale nie podoba mi się to z trzech powodów.
- nie służy żadnemu dodatkowemu celowi poza uspokajaniem
R CMD check
. - nie odzwierciedla intencji. Rodzi to oczekiwanie, że
aes()
wywołanie zobaczy nasze zmienne NULL (nie zrobi tego), jednocześnie zaciemniając prawdziwy cel (uświadomienie R CMD zmiennych, o których inaczej nie wiedziałby, że byłyby związane) - Problemy 1 i 2 mnożą się, ponieważ za każdym razem, gdy piszesz funkcję zwracającą element wydruku, musisz dodawać mylącą instrukcję NULLing
Strategia with ()
Możesz użyć with()
do jawnego zasygnalizowania, że zmienne, o których mowa, można znaleźć w większym środowisku. W moim przypadku użycie with()
wygląda następująco:
JitteredResponsesByContrast <- function (data) {
with(data, {
geom_point(
aes(
x = x.values,
y = y.values
),
data = data,
position = position_jitter(height = 0, width = GetDegreeOfJitter(jj))
)
}
)
}
To rozwiązanie działa. Ale nie podoba mi się to rozwiązanie, ponieważ nie działa tak, jakbym tego oczekiwał. Jeśli with()
naprawdę rozwiązywania problemu wskazując tłumacza do miejsca, gdzie są zmienne, to nie powinien nawet trzeba ten data =
argument. Ale with()
to nie działa w ten sposób:
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
I znów myślę, że to rozwiązanie ma podobne wady do strategii NULLing:
- Nadal muszę przejść przez każdą funkcję elementu wykresu i zawrzeć logikę w
with()
wywołaniu with()
Rozmowa jest mylące. Nadal muszę przedstawićdata =
argument; wszystko cowith()
robi jest uspokajająceR CMD check
.
Wniosek
Z mojego punktu widzenia mogę wziąć trzy opcje:
- Zachęcaj CRAN do zignorowania notatek, argumentując, że są „fałszywe” (zgodnie z zasadami CRAN ) i rób to za każdym razem, gdy przesyłam paczkę
- Napraw mój kod za pomocą jednej z dwóch niepożądanych strategii (NULLing lub
with()
bloki) - Bucz się naprawdę głośno i mam nadzieję, że problem zniknie
Żadna z tych trzech rzeczy mnie nie uszczęśliwia i zastanawiam się, co ludzie sugerują, że ja (i inni programiści pakietów chcący skorzystać z ggplot2) powinienem zrobić. Dzięki wszystkim z góry. Naprawdę doceniam twoje nawet przeczytanie tego :-)
aes_string
transform
isubset
zbyt (nie 100% pewien, ale to ma sens).Odpowiedzi:
Próbowałeś
aes_string
zamiastaes
? To powinno działać, chociaż nie próbowałem:źródło
aes
robi whileaes_string
nie definiuje parametrów pozycyjnychx
iy
.aes_string
mówi: „Wszystkie te funkcje są przestarzałe. Zamiast tego użyj schludnych idiomów oceny (zobacz sekcję quasiquotation w dokumentacji aes ()).” (ggplot2 wersja 3.2.1). To prawdopodobnierlang::.data
najlepszy kandydat do wyciszenia tych notatek.Masz dwa rozwiązania:
Przepisz kod, aby uniknąć niestandardowej oceny. W przypadku ggplot2 oznacza to użycie
aes_string()
zamiastaes()
(zgodnie z opisem Harlana)Dodaj połączenie do
globalVariables(c("x.values", "y.values"))
dowolnego miejsca na najwyższym poziomie pakietu.Podczas przesyłania do CRAN powinieneś dążyć do 0 UWAG w swoim pakiecie, nawet jeśli musisz zrobić coś nieco zhackowanego. Ułatwia to życie CRAN i jest łatwiejsze dla Ciebie.
(Zaktualizowano 31.12.2014, aby odzwierciedlić moje najnowsze przemyślenia na ten temat)
źródło
globalVariables
to ohydny hack i nigdy go nie użyję.ggplot
idata.table
, a zatem ma mnóstwo tych ostrzeżeń, które trzymało mnie z zauważając inne ważniejsze ostrzeżenia, które naprawdę były problemy Musiałem naprawić.ggplot::scale_dualAxis.sqrt
i wykresy kołowe 3D z wzorami wypełnień.To pytanie zostało zadane i udzielono odpowiedzi jakiś czas temu, ale tylko dla informacji, ponieważ od wersji 2.1.0 istnieje inny sposób na obejście notatek:
aes_(x=~x.values,y=~y.values).
źródło
Jeśli
Możesz dodać połączenie na najwyższym poziomie pakietu:
z:
źródło
x.values
iy.values
, więc musiałbym zarejestrować WSZYSTKIE z nich.suppressForeignCheck
jest używanezzz.R
pliku./R/
. Na przykład github.com/HughParsonage/grattan/blob/master/R/zzz.RW 2019 roku najlepszym sposobem na obejście tego jest użycie
.data
prefiksu zrlang
pakietu. To każe R traktowaćx.values
iy.values
jako kolumny wdata.frame
(więc nie będzie narzekać na niezdefiniowane zmienne).Uwaga: Działa to najlepiej, jeśli masz predefiniowane nazwy kolumn, o których wiesz, że będą istnieć w danych wejściowych
źródło
Dodaj ten wiersz kodu do pliku, w którym dostarczasz dokumentację na poziomie pakietu:
Przykład tutaj
źródło