जब मेरा ggplot2 सिंटैक्स समझदार होता है, तो मैं R CMD चेक को "ग्लोबल वेरिएबल के लिए कोई दृश्यमान बंधन" कैसे नहीं संभाल सकता हूं?


180

EDIT: हेडली विकम बताते हैं कि मुझे याद आती है। सीएमडी जांच चेतावनियों को नहीं बल्कि NOTES फेंक रहा है। मैं बहुत भ्रम के लिए माफी चाहता हूँ। यह मेरी देखरेख थी।

लघु संस्करण

R CMD checkइस नोट को हर बार जब मैं ggplot2 में समझदार कथानक-रचना वाक्य-विन्यास का उपयोग करता हूँ :

no visible binding for global variable [variable name]

मैं समझता हूं कि आर सीएमडी जांच क्यों करता है, लेकिन यह अन्यथा समझदार वाक्यविन्यास की पूरी नस को अपराधी बना देता है। मुझे यकीन नहीं है कि मेरे पैकेज को पास करने R CMD checkऔर सीआरएएन में भर्ती होने के लिए क्या कदम उठाना है।

पृष्ठ - भूमि

Sascha Epskamp ने पहले अनिवार्य रूप से एक ही मुद्दे पर पोस्ट किया था । मुझे लगता है कि अंतर यह है कि यहsubset() मेन्यू कहता है कि यह इंटरैक्टिव उपयोग के लिए डिज़ाइन किया गया है

मेरे मामले में, मुद्दा खत्म नहीं हुआ है, subset()बल्कि एक मुख्य विशेषता है ggplot2: data =दलील।

कोड का एक उदाहरण मैं लिखता हूं जो इन नोटों को उत्पन्न करता है

यहाँ मेरे पैकेज में एक उप-कार्य है जो एक प्लॉट में अंक जोड़ता है:

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, इस कोड को पार्स करने पर, कहेगा

granovagg.contr : JitteredResponsesByContrast: no visible binding for
  global variable 'x.values'
granovagg.contr : JitteredResponsesByContrast: no visible binding for
  global variable 'y.values'

क्यों आर सीएमडी जाँच सही है

जाँच तकनीकी रूप से सही है। x.valuesतथाy.values

  • फ़ंक्शन में स्थानीय रूप से परिभाषित नहीं किया गया है JitteredResponsesByContrast()
  • x.values <- [something]विश्व स्तर पर या कॉल करने वाले के रूप में पूर्व-परिभाषित नहीं हैं ।

इसके बजाय, वे एक डेटाफ्रेम के भीतर परिवर्तनशील होते हैं जो पहले परिभाषित हो जाते हैं और फ़ंक्शन में पारित हो जाते हैं JitteredResponsesByContrast()

क्यों ggplot2 R CMD जाँच की अपील करना मुश्किल बनाता है

ggplot2 एक dataतर्क के उपयोग को प्रोत्साहित करता है। डेटा तर्क, संभवतः, इस कोड को निष्पादित करेगा

library(ggplot2)
p <- ggplot(aes(x = hwy, y = cty), data = mpg)
p + geom_point()

लेकिन यह कोड ऑब्जेक्ट-नहीं-मिली त्रुटि का उत्पादन करेगा:

library(ggplot2)
hwy # a variable in the mpg dataset

दो काम-आस-पास, और मैं न तो क्यों खुश हूं

NULLING रणनीति

मैथ्यू डोले ने समस्याग्रस्त चरों को NULL को पहले सेट करने की सिफारिश की, जो मेरे मामले में इस तरह दिखेगी:

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))
    )
  )
}

मैं इस समाधान की सराहना करता हूं, लेकिन मैं इसे तीन कारणों से नापसंद करता हूं।

  1. यह तुष्टिकरण से परे कोई अतिरिक्त उद्देश्य नहीं है R CMD check
  2. यह इरादे को नहीं दर्शाता है। यह इस उम्मीद को जगाता है कि aes()कॉल वास्तविक उद्देश्य को देखते हुए (अब आर सीएमडी जाँच को स्पष्ट रूप से पता नहीं चलेगा)
  3. 1 और 2 की समस्याएं कई गुना बढ़ जाती हैं क्योंकि हर बार जब आप प्लॉट एलिमेंट रिटर्न करते हैं, तो आपको एक भ्रमित करने वाला नॉवेल स्टेटमेंट जोड़ना होगा।

() रणनीति के साथ

आप with()स्पष्ट रूप से संकेत देने के लिए उपयोग कर सकते हैं कि विचाराधीन चर कुछ बड़े वातावरण में पाए जा सकते हैं। मेरे मामले में, with()इस तरह दिखता है:

JitteredResponsesByContrast <- function (data) {
  with(data, {
      geom_point(
               aes(
                 x = x.values, 
                 y = y.values
               ),
               data     = data,
               position = position_jitter(height = 0, width = GetDegreeOfJitter(jj))
      )
    }
  )
}

यह समाधान काम करता है। लेकिन, मुझे यह समाधान पसंद नहीं है क्योंकि यह उस तरीके से भी काम नहीं करता है जिससे मैं इसकी उम्मीद करूंगा। यदि with()वास्तव में जहां चर हैं करने के लिए दुभाषिया ओर इशारा करते हुए की समस्या को हल कर रहे थे, तो मैं भी नहीं करना चाहिए की जरूरत हैdata = तर्क। लेकिन, with()इस तरह से काम नहीं करता है:

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

तो, फिर से, मुझे लगता है कि इस समाधान में NULLing रणनीति के समान दोष हैं:

  1. मुझे अभी भी हर प्लॉट एलिमेंट फ़ंक्शन के माध्यम से जाना है और with()कॉल में तर्क को लपेटना है
  2. with()कॉल भ्रामक है। मुझे अभी भी एक data =तर्क की आपूर्ति करने की आवश्यकता है ; सभी with()खुश है R CMD check

निष्कर्ष

जिस तरह से मैं इसे देखता हूं, तीन विकल्प हैं जो मैं ले सकता हूं:

  1. लॉबी CRAN नोटों की अनदेखी करके यह तर्क देते हैं कि वे " चतुर " ( CRAN नीति के अनुसार ) हैं, और हर बार जब मैं एक पैकेज जमा करता हूं
  2. दो अवांछनीय रणनीतियों (NULLing या with()ब्लॉक) में से एक के साथ मेरा कोड ठीक करें
  3. हम वास्तव में जोर से और आशा है कि समस्या दूर हो जाती है

तीनों में से कोई भी मुझे खुश नहीं करता है, और मैं सोच रहा हूं कि लोग मुझे क्या सुझाव देते हैं (और ggplot2 में टैप करने के लिए अन्य पैकेज डेवलपर्स) को क्या करना चाहिए। सभी को अग्रिम धन्यवाद। मैं वास्तव में इस के माध्यम से भी अपने पढ़ने की सराहना :-)


20
मुझे # 1 और # 3 पसंद है।
बेन बोल्कर

8
@BenBolker वो भी मेरी गो-टू तकनीकें हैं।
हैडले

6
एक 4 वाँ विकल्प है: 'R CMD चेक' को संशोधित करें और विचार के लिए r-devel में एक पैच सबमिट करें। मुझे लगता है कि आपको यह पता लगाना बहुत मुश्किल है (और संभवतः असंभव है) जो पता लगाने के लिए कि जो कि सहज हैं और जो नहीं हैं। अगर कोई भी ऐसा करने के लिए कोड का एक टुकड़ा लेकर आया है, तो ...
मैट डाउल

6
एक और रणनीति का उपयोग करना हैaes_string
हैडल

2
यह ( transformऔर subset100% यकीन नहीं है, लेकिन यह समझ में आता है) के साथ एक समस्या है ।
ब्रोडिएग

जवाबों:


45

क्या आपने aes_stringइसके बजाय कोशिश की है aes? यह काम करना चाहिए, हालांकि मैंने इसकी कोशिश नहीं की है:

aes_string(x = 'x.values', y = 'y.values')

4
बस एक चेतावनी: aesजबकि करता aes_stringस्थितीय मापदंडों को परिभाषित नहीं करता xऔर y
टॉपचेफ

6
बस एक और चेतावनी। aes_string आपको x और y मानों में हेरफेर करने के लिए फ़ंक्शन का उपयोग करने की अनुमति नहीं देता है। यह कहें कि आप परिवर्तन y को लॉग करना चाहते हैं जिस स्थिति में aes_string (x = 'x.values', y = 'log (y.values)') निश्चित रूप से काम नहीं करता है। मैं इस तरह के परिवर्तनों का उपयोग खुद बहुत करता हूं इसलिए aes_string हमेशा मेरे लिए एक विकल्प नहीं है।
डॉ। माइक

शायद इस उत्तर को (और सबसे अधिक मतों के साथ) को अपडेट किया जाना चाहिए क्योंकि यह aes_stringकहता है: "ये सभी कार्य नरम हो गए हैं। कृपया इसके बजाय स्पष्ट मूल्यांकन मुहावरों का उपयोग करें। (ggplot2 संस्करण 3.2.1)। शायद rlang::.dataइन नोटों को चुप कराने के लिए सबसे अच्छा उम्मीदवार है।
वंडेनमैन

86

आपके पास दो समाधान हैं:

  • गैर-मानक मूल्यांकन से बचने के लिए अपने कोड को फिर से लिखें। Ggplot2 के लिए, इसका मतलब aes_string()है aes()( हार्लान द्वारा वर्णित के बजाय )

  • globalVariables(c("x.values", "y.values"))अपने पैकेज के शीर्ष-स्तर में कहीं न कहीं एक कॉल जोड़ें ।

CRAN को सबमिट करते समय आपको अपने पैकेज में 0 NOTES के लिए प्रयास करना चाहिए, भले ही आपको कुछ थोड़ा हैक करना पड़े। यह CRAN के लिए जीवन को आसान बनाता है, और आपके लिए आसान है।

(इस पर मेरे नवीनतम विचारों को प्रतिबिंबित करने के लिए 2014-12-31 अपडेट किया गया)


26
globalVariablesएक गुप्त हैक है और मैं इसका उपयोग कभी नहीं करूंगा।
हैडली

10
क्या मूल्य है, मेरे पैकेज को इन नोटों की वजह से खारिज कर दिया गया था और कहा गया था कि इसका उपयोग करने के लिए :: GlobalVariables फ़ंक्शन। चूंकि मैं बहस करने की स्थिति में नहीं हूं, इसलिए मैंने यही किया।
jbryer

9
मैं मानता हूँ कि यह उन्हें अनदेखा करने के लिए सबसे अच्छा होगा, लेकिन के अपने कोड का उपयोग करता है बहुत से ggplotऔर data.table, और इस प्रकार है टन इन चेतावनियों, जो मुझे अन्य अधिक महत्वपूर्ण चेतावनी है कि वास्तव में समस्याओं मैं ठीक करने के लिए आवश्यक थे देख से रखा है की।
केन विलियम्स

108
@ महादेव आपको यह नहीं कहना चाहिए कि आप कभी भी चीजों का उपयोग नहीं करेंगे जब केवल दो साल बाद आपको लगता है कि यह ठीक है
हैडले

10
नए साल के संकल्प? मैं अपनी आंखों ggplot::scale_dualAxis.sqrtको भरने के पैटर्न के साथ 3 डी पाई चार्ट के लिए खुली रखूंगा ।
बपतिस्मा

29

इस सवाल का जवाब दिया गया है और थोड़ी देर पहले ही जवाब दिया गया है लेकिन आपकी जानकारी के लिए, संस्करण 2.1.0 के बाद से नोटों को पाने का एक और तरीका है:aes_(x=~x.values,y=~y.values).


12

अगर

getRversion() >= "3.1.0"

आप पैकेज के शीर्ष स्तर पर कॉल जोड़ सकते हैं:

utils::suppressForeignCheck(c("x.values", "y.values"))

से:

help("suppressForeignCheck")

3
यह एक उचित समाधान है। धन्यवाद! मैंने इस पर विचार किया, लेकिन समस्या यह है कि मेरे पास बहुत से वैरिएबल हैं जैसे x.valuesऔर y.values, इसलिए मुझे उन सभी को पंजीकृत करना होगा।
रिश्वत

4
यह है कि क्या नहीं suppressForeignCheckहै
हैडले

10
वास्तव में शीर्ष स्तर कहां है ? इस आदेश को किस फ़ाइल में जोड़ूँ?
ड्रमरोड

9
कस्टम द्वारा, इसे एक zzz.Rफ़ाइल में डाला जाता है ./R/। उदाहरण के लिए, github.com/HughParsonage/grattan/blob/master/R/zzz.R
Hugh

6
@ महादली, इसका क्या उपयोग है? मदद ("suppressForeignCheck") का अर्थ है कि यह "रन-टाइम कैलकुलेट किए गए देशी सिंबल" के लिए है, लेकिन बिल्ली क्या है?
पीडीबी

8

2019 में, इसके चारों ओर प्राप्त करने का सबसे अच्छा तरीका पैकेज .dataसे उपसर्ग का उपयोग करना है rlang। यह आर को इलाज के लिए x.valuesऔर y.valuesएक स्तंभ के रूप में बताता है data.frame(इसलिए यह अपरिभाषित चर के बारे में शिकायत नहीं करेगा)।

नोट: यह सबसे अच्छा काम करता है अगर आपके पास पूर्वनिर्धारित कॉलम नाम हैं जिन्हें आप जानते हैं कि आप डेटा इनपुट में मौजूद होंगे

#' @importFrom rlang .data
my_func <- function(data) {
    ggplot(data, aes(x = .data$x, y = .data$y))
}

3

उस फ़ाइल में कोड की पंक्ति जोड़ें जिसमें आप पैकेज-स्तरीय दस्तावेज़ प्रदान करते हैं:

if(getRversion() >= "2.15.1")  utils::globalVariables(c("."))

यहाँ उदाहरण है

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.