варианты pmap_, работающие с data.frames в виде списков - PullRequest
1 голос
/ 03 июня 2019

У меня есть воспоминание о том, что purrr::pmap_* может рассматривать data.frame как список, но синтаксис ускользает от меня.

Представьте, что мы хотим разместить отдельный объект lm для каждого значения mtcars$vs и mtcars$am

library(tidyverse)
library(broom)

d1 <- mtcars %>% 
  group_by(
    vs, am
  ) %>% 
  nest %>% 
  mutate(
    coef = data %>% 
      map(
        ~lm(mpg ~ wt, data =.) %>% 
          tidy
      )
  )

Если бы я хотел извлечь оценки коэффициентов как не вложенныеdata.frame и добавьте значения am и vs, я мог бы попробовать

d1[, -3] %>% 
  pmap_dfr(
    function(i, j, k)
      k %>% 
      mutate(
        vs = i,
        am = j
      )
  )

Но это приводит к ошибке.Более явное объявление этих переменных как отдельных списков дает желаемый эффект

list(
  d1$vs,
  d1$am,
  d1$coef
  ) %>% 
  pmap_dfr(
    function(i, j, k)
      k %>% 
      mutate(
        vs = i,
        am = j
      )
  )

Существует ли краткий способ для pmap_* обрабатывать data.frame как список?

Ответы [ 2 ]

3 голосов
/ 03 июня 2019

Мы можем использовать стандартную опцию для извлечения компонентов (..1, ..2 и т. Д.)

d1[, -3]  %>% 
    pmap_dfr(~ ..3 %>%
                  mutate(vs = ..1, am = ..2))
# A tibble: 8 x 7
#  term        estimate std.error statistic   p.value    vs    am
#  <chr>          <dbl>     <dbl>     <dbl>     <dbl> <dbl> <dbl>
#1 (Intercept)    42.4      3.30      12.8  0.000213      0     1
#2 wt             -7.91     1.14      -6.93 0.00227       0     1
#3 (Intercept)    44.1      6.96       6.34 0.00144       1     1
#4 wt             -7.77     3.36      -2.31 0.0689        1     1
#5 (Intercept)    31.5      8.98       3.51 0.0171        1     0
#6 wt             -3.38     2.80      -1.21 0.281         1     0
#7 (Intercept)    25.1      3.51       7.14 0.0000315     0     0
#8 wt             -2.44     0.842     -2.90 0.0159        0     0
2 голосов
/ 03 июня 2019

Это потому, что второй список не имеет атрибута names. Если вы unname d1, это работает. Тот факт, что вы использовали функцию list во втором примере, не имеет значения (за исключением того, что она удалила имена), поскольку оба объекта являются списками (фреймы данных являются списками).

d1[, -3] %>% 
  unname %>% 
  pmap_dfr(
    function(i, j, k)
      k %>% 
      mutate(
        vs = i,
        am = j
      )
  )


# # A tibble: 8 x 7
#   term        estimate std.error statistic   p.value    vs    am
#   <chr>          <dbl>     <dbl>     <dbl>     <dbl> <dbl> <dbl>
# 1 (Intercept)    42.4      3.30      12.8  0.000213      0     1
# 2 wt             -7.91     1.14      -6.93 0.00227       0     1
# 3 (Intercept)    44.1      6.96       6.34 0.00144       1     1
# 4 wt             -7.77     3.36      -2.31 0.0689        1     1
# 5 (Intercept)    31.5      8.98       3.51 0.0171        1     0
# 6 wt             -3.38     2.80      -1.21 0.281         1     0
# 7 (Intercept)    25.1      3.51       7.14 0.0000315     0     0
# 8 wt             -2.44     0.842     -2.90 0.0159        0     0

Вы можете также назвать аргументы в функции вашего первого блока кода для соответствия (или использовать ..1 и т. Д.) Для того же результата

d1[, -3] %>% 
  pmap_dfr(
    function(vs, am, coef)
      coef %>% 
      mutate(
        vs = vs,
        am = am
      )
  )


# # A tibble: 8 x 7
#   term        estimate std.error statistic   p.value    vs    am
#   <chr>          <dbl>     <dbl>     <dbl>     <dbl> <dbl> <dbl>
# 1 (Intercept)    42.4      3.30      12.8  0.000213      0     1
# 2 wt             -7.91     1.14      -6.93 0.00227       0     1
# 3 (Intercept)    44.1      6.96       6.34 0.00144       1     1
# 4 wt             -7.77     3.36      -2.31 0.0689        1     1
# 5 (Intercept)    31.5      8.98       3.51 0.0171        1     0
# 6 wt             -3.38     2.80      -1.21 0.281         1     0
# 7 (Intercept)    25.1      3.51       7.14 0.0000315     0     0
# 8 wt             -2.44     0.842     -2.90 0.0159        0     0

Вы также можете использовать wap из экспериментального рэп-пакета

library(rap)

d1[, -3] %>% 
  wap( ~ coef %>% 
          mutate(
            vs = vs,
            am = am)) %>% 
  bind_rows
# # A tibble: 8 x 7
#   term        estimate std.error statistic   p.value    vs    am
#   <chr>          <dbl>     <dbl>     <dbl>     <dbl> <dbl> <dbl>
# 1 (Intercept)    42.4      3.30      12.8  0.000213      0     1
# 2 wt             -7.91     1.14      -6.93 0.00227       0     1
# 3 (Intercept)    44.1      6.96       6.34 0.00144       1     1
# 4 wt             -7.77     3.36      -2.31 0.0689        1     1
# 5 (Intercept)    31.5      8.98       3.51 0.0171        1     0
# 6 wt             -3.38     2.80      -1.21 0.281         1     0
# 7 (Intercept)    25.1      3.51       7.14 0.0000315     0     0
# 8 wt             -2.44     0.842     -2.90 0.0159        0     0
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...