Subset of df in string state

I want to multiply df

in an unknown state (let's say randomly, like in the example below):

df <- data.frame(a=1:10, b = 10:1)
condition <- paste0(sample(letters[1:2],1), sample(c("<",">"),1), sample(1:10,1))

      

I can do it with eval

, which, vox populi, is suboptimal:

subset(df, eval(parse(text=condition)))

      

Is there any alternative eval(parse)

?

+3


source to share


4 answers


With a little adaptation to your script, if this becomes more doable:

condition  <- list(value1 = sample(letters[1:2], 1),
                   comp =   sample(c(`<`, `>`), 1)[[1]],
                   value2 = sample(1:10, 1))

subset(df, condition$comp(df[, condition$value1], condition$value2))

      



So it depends on the constraints on how your state is passed.

(Note that using subset

might be a bad idea)

+2


source


If some constraints can be introduced, such as data containing only numeric columns and only linear conditions, you can formulate the conditional solution as dot products:



# a > b
condition.mat <- c(1, -1)
condition.const <- 0

# b > 4
# condition.mat <- c(0, 1)
# condition.const <- 4

dec <- as.matrix(df) %*% condition.mat - condition.const
sel <- dec > 0

print(df[sel,])

      

+1


source


An alternative to the base subset

is a function filter

from dplyr

:

df <- data.frame(a=1:10, b = 10:1)
condition <- paste0(sample(letters[1:2],1), sample(c("<",">"),1), sample(1:10,1))

library(dplyr)
df %>% filter(eval(parse(text=condition))

      

+1


source


Just one thought. There are other ways to save dynamic code without the (nasty) "symbolic expression", for example:

df <- data.frame(a=1:10, b = 10:1)

mysubset <- function (f,x1,x2) {
  df[f(df[[x1]],x2),]
}

mycol <- sample(letters[1:2],1) 
myfun <- sample(c("<",">"),1)
mylimit <- sample(1:10,1)

mysubset(.Primitive(myfun),mycol,mylimit) # in my mind just as dynamic as eval-parse ..

mysubset(`<`,"a",4) 

      

+1


source







All Articles