функции в кадре данных - PullRequest
1 голос
/ 14 апреля 2020

Я хотел бы создать список функций и поместить их в кадр данных. Это облегчает мне манипулирование функциями для остальной части моей работы. Я хочу поместить функции ecdf и quantile при группировании по столбцам символов / факторов.

Я сделал что-то вроде этого:

library(tidyverse)
quantilef = function(x) {
  qf = function(p){
    return(quantile(x, probs = p))
  }
  return(qf)
}

ecdfdf = iris %>%
  group_by(Species) %>%
  summarise(ecdf_ = list(ecdf(Sepal.Length)),
            qf_ = list(quantilef(x = Sepal.Length)))

Ecdf работает, как и ожидалось:

> ecdfdf %>% mutate(p = map_dbl(.x = ecdf_, .f = ~.x(5)))
# A tibble: 3 x 4
  Species    ecdf_  qf_        p
  <fct>      <list> <list> <dbl>
1 setosa     <ecdf> <fn>    0.56
2 versicolor <ecdf> <fn>    0.06
3 virginica  <ecdf> <fn>    0.02

Но квантиль дает NA:

> ecdfdf %>% mutate(q10 = map_dbl(.x = qf_, .f = ~.x(0.5)))
# A tibble: 3 x 4
  Species    ecdf_  qf_      q10
  <fct>      <list> <list> <dbl>
1 setosa     <ecdf> <fn>      NA
2 versicolor <ecdf> <fn>      NA
3 virginica  <ecdf> <fn>      NA

Я знаю, что quantilef работает, потому что он работает вне фрейма данных:

> qfsl = quantilef(x = iris$Sepal.Length)
> qfsl(0.5)
50% 
5.8 

Что происходит? Как мне обойти это?

1 Ответ

3 голосов
/ 14 апреля 2020

Мне кажется, проблема в том, что когда вы создаете список функций для qf_, вы передаете параметр x, который лениво вычисляется. Когда вы go вызываете функцию, x больше не существует в вызывающей среде.

Одним из способов решения этой проблемы является перенос x в quosure, который оценивается в точке, функция называется.

Вот репрезекс:

library(tidyverse)

quantilef = function(x) {
  y <- rlang::new_quosure(x)
  qf <- function(p){
    return(quantile(rlang::eval_tidy(y), probs = p))
  }
  return(qf)
}

ecdfdf = iris %>%
  group_by(Species) %>%
  summarise(ecdf_ = list(ecdf(Sepal.Length)),
            qf_ = list(quantilef(x = Sepal.Length)))

ecdfdf %>% mutate(q10 = map_dbl(.x = qf_, .f = ~.x(0.5)))
#> # A tibble: 3 x 4
#>   Species    ecdf_  qf_      q10
#>   <fct>      <list> <list> <dbl>
#> 1 setosa     <ecdf> <fn>     5  
#> 2 versicolor <ecdf> <fn>     5.9
#> 3 virginica  <ecdf> <fn>     6.5

Создан в 2020-04-14 пакетом prex (v0.3.0)

...