David Krider
David Krider

Reputation: 11

Variable name collision in dplyr

I am attempting to compute a moving median on a variable contained within a data.frame using dplyr. The problem I am running into is that the function that I am passing into rollapply() has the same name as a variable in the original data.frame. For example:

df <- data.frame(median = seq(1:100))

df %>%
  mutate(ln_median = log(median)) %>%
  mutate(ln_median_10 = rollapply(ln_median, 5, median))

Generates the error message:

Error in eval(substitute(expr), envir, enclos) : '1:100' is not a function, character or symbol

The underlying cause is that the median in the rollapply() is resolving to the variable in the data.frame and not the function "median". I have been able to get around this with the following code:

df %>% mutate(ln_median = log(median)) %>%
       mutate(ln_median_10 = rollapply(ln_median, 5, function(a) median(a), fill = NA))

That is, by wrapping the median function in order to suppress it from being interpreted as a variable within the data.frame.

Is there a more elegant way of achieving the same thing?

Upvotes: 1

Views: 187

Answers (3)

Retired Data Munger
Retired Data Munger

Reputation: 1445

have you tried to pass the function name in as

stats::median

Upvotes: 1

moodymudskipper
moodymudskipper

Reputation: 47300

If it was really the issue (but I can't reproduce it either), you could use match.fun("median") instead of median

Upvotes: 0

acylam
acylam

Reputation: 18661

As @lebelinoz mentioned in the comments, you can use fill = NA to solve the unequal length error. Not able to reproduce your error though. Also note that mutate allows you to use a variable you have just created within the same function. So no need for the second mutate:

library(zoo)

df %>%
  mutate(ln_median = log(median),
         ln_median_10 = rollapply(ln_median, 5, median, fill = NA))

Upvotes: 0

Related Questions