Home > Software design >  Understanding `purrr::pmap` with a dataframe inside `mutate` in R
Understanding `purrr::pmap` with a dataframe inside `mutate` in R

Time:10-28

I want to make the sum of the first 3 columns with pmap.

library(tidyverse)

mtcars %>% 
  mutate(new = pmap(select(., 1:3), ~ sum(.))) # FAILS

mtcars %>% 
  mutate(new = pmap(., ~ sum(.[1:3]))) # FAILS

                     mpg cyl  disp  hp drat    wt  qsec vs am gear carb new
Mazda RX4           21.0   6 160.0 110 3.90 2.620 16.46  0  1    4    4  NA
Mazda RX4 Wag       21.0   6 160.0 110 3.90 2.875 17.02  0  1    4    4  NA
Datsun 710          22.8   4 108.0  93 3.85 2.320 18.61  1  1    4    1  NA

I know how to do it with rowwise or RowSums but I want a solution with pmap.

CodePudding user response:

A pmap solution would be:

mtcars %>% 
  mutate(new = pmap(., ~ sum(..1, ..2, ..3)))

Or, slightly better IMO:

mtcars %>% 
  mutate(new = pmap(select(., 1:3), sum)) 

mtcars %>% 
  mutate(new = pmap(select(., 1:3), ~ sum(...))) 

Or, event better, by combining with across:

mtcars %>% 
  mutate(new = pmap(across(1:3), sum))

CodePudding user response:

Why does mtcars %>% mutate(new = pmap(select(., 1:3), ~ sum(.))) fail?

In your code sum(.) is equal to sum(..1). It only uses the first variable but if you would like to take all 3 in your function call you could modify it as:

mtcars %>% mutate(new = pmap(select(., 1:3), ~ sum(c(...))))

Simply replacing . with c(...) would do.

CodePudding user response:

I know you said you want to have a pmap solution, but my favourite way of avoiding the very slow rowwise is a combination of across and apply:

mtcars |>
  mutate(new = apply(across(1:3), 1, sum))

                     mpg cyl  disp  hp drat    wt  qsec vs am gear carb   new
Mazda RX4           21.0   6 160.0 110 3.90 2.620 16.46  0  1    4    4 187.0
Mazda RX4 Wag       21.0   6 160.0 110 3.90 2.875 17.02  0  1    4    4 187.0
Datsun 710          22.8   4 108.0  93 3.85 2.320 18.61  1  1    4    1 134.8
Hornet 4 Drive      21.4   6 258.0 110 3.08 3.215 19.44  1  0    3    1 285.4
Hornet Sportabout   18.7   8 360.0 175 3.15 3.440 17.02  0  0    3    2 386.7
Valiant             18.1   6 225.0 105 2.76 3.460 20.22  1  0    3    1 249.1
...
  • Related