bill999
bill999

Reputation: 2529

How to perform function on certain columns and then perform another function on that

Say that I have these data:

a <- data.frame(group=c("one", "two", "three"), a = c(1,2,3), b=c(4,3,5), c=c(8,2,1))

  group a b c
1   one 1 4 8
2   two 2 3 2
3 three 3 5 1

I would like to perform a function on the 2nd-4th columns and then perform another function on those results. In particular, I would like to square each of these columns, and then add the results together.

This is what I would like to obtain:

  group a b c want
1   one 1 4 8   81
2   two 2 3 2   17
3 three 3 5 1   35

(For the first row, 81 is obtained by 1^2 + 4^2 + 8^2.

I have a sense that this might involve something like lapply, but I am not sure.

Note that I would like to do this using something other than something like

a %>% mutate(want = a^2 + b^2 + c^2)

(as in principle there could be thousands of columns to consider).

Solutions in base R as well as tidyverse are appreciated.

Upvotes: 1

Views: 28

Answers (2)

ThomasIsCoding
ThomasIsCoding

Reputation: 101014

A base R option

a$want <- rowSums(a[-1]^2)

gives

> a
  group a b c want
1   one 1 4 8   81
2   two 2 3 2   17
3 three 3 5 1   35

Upvotes: 1

akrun
akrun

Reputation: 886928

We could select the columns, get the power and reduce to return the sum

library(dplyr)
library(purrr)
a %>%
     mutate(want = select(cur_data(), -group)^2 %>% 
                  reduce(`+`))

-output

  group a b c want
1   one 1 4 8   81
2   two 2 3 2   17
3 three 3 5 1   35

Or use rowSums

a %>% 
    mutate(want = rowSums(select(cur_data(), -group)^2, na.rm = TRUE))

-output

   group a b c want
1   one 1 4 8   81
2   two 2 3 2   17
3 three 3 5 1   35

Or if the function used is other than ^, can also loop across the columns and then add (+) with reduce or use rowSums

a %>% 
    mutate(want = rowSums(across(-group, ~ .^2)))
  group a b c want
1   one 1 4 8   81
2   two 2 3 2   17
3 three 3 5 1   35

Upvotes: 1

Related Questions