2016-08-30 15 views
5

का उपयोग करके दोहराए गए चर को दोहराएं। मैं आर में स्वयं सिखाया गया हूं और यह मेरा पहला स्टैक ओवरफ्लो प्रश्न है। मैं क्षमा चाहता हूं अगर यह एक स्पष्ट मुद्दा है; कृप्या दयालु बनें।दोहराए गए और purrr

लघु मेरी प्रश्न
के संस्करण मैं वर्ष की तुलना में एक चर वर्ष में प्रतिशत परिवर्तन की गणना करने के लिए एक कस्टम समारोह लिखा था। मैं परिवर्तनीय नामों के वेक्टर में अपना कस्टम फ़ंक्शन लागू करने के लिए purrr के map_at फ़ंक्शन का उपयोग करना चाहता हूं। जब एक ही वैरिएबल पर लागू मेरे कस्टम समारोह काम करता है, लेकिन जब मैं का उपयोग कर map_a

मेरे कस्टम समारोह

calculate_delta <- function(df, col) { 

    #generate variable name 
    newcolname = paste("d", col, sep="") 

    #get formula for first difference. 
    calculate_diff <- lazyeval::interp(~(a + lag(a))/a, a = as.name(col)) 

    #pass formula to mutate, name new variable the columname generated above 
    df %>% 
     mutate_(.dots = setNames(list(calculate_diff), newcolname)) } 

जब मैं mtcars डाटासेट में एक भी चर को यह समारोह लागू यह श्रृंखला विफल रहता है, आउटपुट अपेक्षित है (हालांकि स्पष्ट रूप से परिणाम का अर्थ गैर-संवेदी है)। का उपयोग करते हुए Purrr

मुझे लगता है कि मैं मुसीबत conceptualizing कैसे map_at कार्य करने के लिए तर्क गुजरता हो रही है एक चरित्र वेक्टर के लिए समारोह लागू करने के लिए

calculate_delta(mtcars, "wt") 

प्रयास। उदाहरण के स्निपेट्स के सभी उदाहरण मैं is.character जैसे कार्यों के साथ map_at का उपयोग कर सकते हैं, जिन्हें अतिरिक्त तर्कों की आवश्यकता नहीं है। purrr का उपयोग करके फ़ंक्शन को लागू करने के मेरे प्रयास यहां दिए गए हैं।

vars <- c("wt", "mpg") 
mtcars %>% map_at(vars, calculate_delta) 

यह मैं इस त्रुटि संदेश

Error in paste("d", col, sep = "") : argument "col" is missing, with no default

मुझे लगता है इस वजह से map_at df रूप vars गुजर रहा है, और col के लिए एक तर्क गुजर नहीं देता है।

vars <- c("wt", "mpg") 
mtcars %>% map_at(vars, calculate_delta, df = .) 

मुझे इस त्रुटि फेंकता है कि:

Error: unrecognised index type 

मैं भर से df तर्क को दूर करने सहित विभिन्न संस्करणों के एक समूह के साथ monkeyed है कि समस्या के समाधान पाने के लिए, मैं निम्नलिखित की कोशिश की calculate_delta फ़ंक्शन, लेकिन मुझे कोई भाग्य नहीं मिला है।

अन्य संभावित समाधानों

1) sapply, बजाय purrr का उपयोग कर इस का एक संस्करण। मैंने इस तरह की समस्या को हल करने की कोशिश की है और इसी तरह की परेशानी थी। और मेरा लक्ष्य purrr का उपयोग करके ऐसा करने का एक तरीका पता करना है, यदि यह संभव है। purrr की मेरी समझ के आधार पर, यह एक सामान्य उपयोग मामले की तरह लगता है।

2) मैं स्पष्ट रूप से सोच सकता हूं कि मैं इसे लूप के उपयोग से कैसे कार्यान्वित करूँगा, लेकिन अगर मैं इसी कारण से संभव हो तो इससे बचने की कोशिश कर रहा हूं।

स्पष्ट रूप से मैं इस गलत के बारे में सोच रहा हूं। कृपया सहायता कीजिए!

संपादित करें 1

स्पष्ट करने के लिए, मैं उत्सुक हूँ अगर वहाँ बार-बार बदलने चर कि दो बातें सिद्ध करने का एक तरीका है।

1) मूल tbl_df के भीतर नए चर उत्पन्न करता है बिना कॉल किए गए कॉलम को प्रतिस्थापित करने के बदले (जैसा कि dplyr के mutate_at का उपयोग करते समय) है।

2) स्वचालित रूप से नए परिवर्तनीय लेबल उत्पन्न करता है।

3) यदि संभव हो, तो map_at का उपयोग करके एक एकल फ़ंक्शन को लागू करके मैंने जो वर्णन किया है उसे पूरा करता है।

यह हो सकता है कि यह संभव नहीं है, लेकिन मुझे लगता है कि जो कुछ मैं वर्णन कर रहा हूं उसे पूरा करने के लिए एक शानदार तरीका होना चाहिए। आप के बाद नए नाम एम्बेड करने के लिए चाहते हैं, तो

delta <- function(x) (x + dplyr::lag(x)) /x 
cols <- c("wt", "mpg") 

#This 
library(dplyr) 
mtcars %>% mutate_at(cols, delta) 
#Or 
library(purrr) 
mtcars %>% map_at(cols, delta) 

#If necessary, in a function 
f <- function(df, cols) { 
    df %>% mutate_at(cols, delta) 
} 

f(iris, c("Sepal.Width", "Petal.Length")) 
f(mtcars, c("wt", "mpg")) 

संपादित

, एक कस्टम पाइप के लिए तैयार समारोह हम लिख सकते हैं:

+2

आपका कार्य 'उत्परिवर्तन' या इसी तरह की संरचना में रखने के लिए तैयार नहीं है। 'Mtcars%>% mutate (countate_delta (wt)) 'यह देखने के लिए कि' purrr' या 'map' के बिना भी यह काम नहीं करता है। यदि यह सामान्य 'dplyr' कॉल के साथ काम नहीं करता है, तो वह उस संरचना में काम नहीं करेगा। इसे फिर से लिखा जाना चाहिए। आप डेटा फ्रेम विनिर्देश की आवश्यकता को हटाकर शुरू कर सकते हैं। इस बारे में सोचें कि कॉल के हिस्से के रूप में 'sum' या' mean' को डेटा फ्रेम की आवश्यकता नहीं है, वे वैक्टर के लिए बनाए गए हैं। –

+0

धन्यवाद, यह इस मुद्दे के बारे में सोचने का एक सहायक तरीका है। यह फ़ंक्शन, नीचे @PierreLafortune से, एक dplyr mutate कॉल के हिस्से के रूप में काम करता है: 'डेल्टा <- फ़ंक्शन (x) (x + dplyr :: lag (x))/x' और यह 'purrr' के साथ भी काम करता है। जैसा कि मैंने नीचे बताया है, वह हिस्सा जो मुझे ट्रिप कर रहा है वह गतिशील रूप से चर का नाम बदल रहा है। –

उत्तर

9

प्रक्रिया को सरल प्रयास करें

Rename <- function(object, old, new) { 
    names(object)[names(object) %in% old] <- new 
    object 
} 

mtcars %>% 
    mutate_at(cols, delta) %>% 
    Rename(cols, paste0("lagged",cols)) 

यदि आप परिणामी अंतराल चर का नाम बदलना चाहते हैं:

mtcars %>% mutate_at(cols, funs(lagged = delta)) 
+0

आपकी प्रतिक्रिया के लिए धन्यवाद। ये समाधान ज्यादातर परिणाम उत्पन्न करते हैं जिन्हें मैं ढूंढ रहा हूं, लेकिन वे मूल चर के साथ मूल चर को बदलकर ऐसा करते हैं। [यह पोस्ट] (http://stackoverflow.com/questions/38340180/automatically-generate-new-variable-names-using-dplyr-mutate) 'mutate_each' के भीतर गतिशील रूप से परिवर्तनीय नाम बदलने का एक तरीका दिखाता है, लेकिन मैं' एक वर्ण वेक्टर को 'वर्स' के तर्क के रूप में पास नहीं करते हैं। –

+0

आपको गतिशील रूप से नाम बदलने की आवश्यकता नहीं है। बस इसके बाद नाम बदलें। या यदि आपको पाइप में इसकी आवश्यकता है तो एक कस्टम फ़ंक्शन लिखें। –

+0

फिर से धन्यवाद, पियरे। आपके द्वारा वर्णित विधि में चरम चर के साथ परिवर्तित होने वाले चर को बदलने का नुकसान होता है। जैसा कि मैंने अपनी मूल पोस्ट के "संपादन 1" में वर्णित किया है, मेरा लक्ष्य मूल चर को प्रतिस्थापित किए बिना फ़ंक्शन को लागू करना है, और गतिशील रूप से एक ही चरण में नाम उत्पन्न करना है। –

संबंधित मुद्दे