11

I have a data frame like this

> df
Source: local data frame [4 x 4]

      a x y z
1 name1 1 1 1
2 name2 1 1 1
3 name3 1 1 1
4 name4 1 1 1

Want to mutate it by adding columns x, y, and z (there can be many more numeric columns). Trying to exclude column 'a' as follows is not working.

dft <- df %>% mutate(funs(total = rowSums(.)), -a)
Error: not compatible with STRSXP

This also produces an error:

dft <- df %>% mutate(total = rowSums(.), -a)
Error in rowSums(.) : 'x' must be numeric

What is the right way?

zx8754
  • 52,746
  • 12
  • 114
  • 209
Gopala
  • 10,363
  • 7
  • 45
  • 77

3 Answers3

18

If you want to keep non-numeric columns in the result, you can do this:

dat %>% mutate(total=rowSums(.[, sapply(., is.numeric)]))

UPDATE: Now that dplyr has scoped versions of its standard verbs, here's another option:

dat %>% mutate(total=rowSums(select_if(., is.numeric)))

UPDATE 2: With dplyr 1.0, the approaches above will still work, but you can also do row sums by combining rowwise and c_across:

iris %>% 
  rowwise %>% 
  mutate(row.sum = sum(c_across(where(is.numeric))))
eipi10
  • 91,525
  • 24
  • 209
  • 285
8

You can use rich selectors with select() inside the call to rowSums()

df %>% transmute(a, total = rowSums(select(., -a)))
jenswirf
  • 7,087
  • 11
  • 45
  • 65
  • I think this is the most general answer and it works in case you want to remove a numerical column as well. It could also be written as `df %>% mutate(total = rowSums(select(., -a)))` – Rodrigo Lustosa Jan 17 '23 at 19:07
1

This should work:

#dummy data    
df <- read.table(text="a x y z

1 name1 1 1 1
2 name2 1 1 1
3 name3 1 1 1
4 name4 1 1 1",header=TRUE)

library(dplyr)

df %>% select(-a) %>% mutate(total=rowSums(.)) 

First exclude text column - a, then do the rowSums over remaining numeric columns.

zx8754
  • 52,746
  • 12
  • 114
  • 209