0

I have an r dataframe of the form:

cond.expr <- data.frame("label" = c("foo", "bar", "baz"), 
                 "dim" = c("long","lat","long"), 
                 "cond" = c("!=", ">", "=="), 
                 "value" = c(NA, 0, 5))

I would like to read cond.expr as a set of conditional expressions that can subsequently be applied to a data set. So if I have the following data set:

data <- data.frame("label" = c("foo", "foo", "bar", "bar","baz","baz"), 
                   "long" = c(NA, 40,35,30,5,0), 
                   "lat" = c(2,3,1,-1,0,4 ))

And apply something of the form filter(data, cond.expr) I should get the following result:

  label long lat
1   foo   40   3
2   bar   30  -1
3   baz    0   4

I wondered if some form of AST for the conditional expression would work here?

Anthony W
  • 1,289
  • 2
  • 15
  • 28
  • 1
    Might be helpful https://stackoverflow.com/questions/55807468/evaluate-different-logical-conditions-from-string-for-each-row/ – Ronak Shah Sep 01 '19 at 09:40

1 Answers1

2

The condition needs to be vector of characters where you specify within single quotes you specify the series of conditions: 'my_cond > a'

library(tidyverse)

cond.expr <- c(
  'label %in% c("foo", "bar", "baz")',
  !is.na(long),
  'lat > 0' ,
  'long == 5' 
  )

data <- data.frame(label = c("foo", "foo", "bar", "bar","baz","baz"), 
                   long = c(NA, 40,35,30,5,0), 
                   lat = c(2,3,1,-1,0,4 )) %>% as_data_frame()

We then create a function that will parse the expression and then unquote it inside filter


filter_conditions <- function(the_data,  filter_statement ) {
  filter_statement_expr <- rlang::parse_expr(filter_statement)

  the_data %>%
    dplyr::filter(!!filter_statement_expr)
}



filter_conditions(data, cond.expr)

Finally we run our new function on data

filter_conditions(data, cond.expr)

# A tibble: 1 x 3
  label  long   lat
  <fct> <dbl> <dbl>
1 baz       5     0