blue-sky
blue-sky

Reputation: 53786

Summing a dataframe with lapply

Here I'm attempting to sum the columns for c1,c2,c3 and add total to a new column in res dataframe :

res <- data.frame("ID" = c(1,2), "c1" = c(1,2), "c2" = c(3,4), "c3" = c(5,6))
res_subset <- data.frame(res$c1 , res$c2 , res$c3)
tr <- t(res_subset)
s1 <- lapply(tr , function(x){
  sum(x)  
})

s1 contains :

s1
[[1]]
[1] 1

[[2]]
[1] 3

[[3]]
[1] 5

[[4]]
[1] 2

[[5]]
[1] 4

[[6]]
[1] 6

I take the transpose of the columns to be summed ( tr <- t(res_subset) ) as lapply executes function against each column but I'm attempting to execute function against row.

Is there an issue with how I take transpose as this appears to work for simpler example :

res1 <- data.frame("c1" = c(1,2), "c2" = c(3,4), "c3" = c(5,6))
lapply(res1 , function(x){
  sum(x)  
})

returns :

$c1
[1] 3

$c2
[1] 7

$c3
[1] 11

Upvotes: 0

Views: 269

Answers (2)

Ernest A
Ernest A

Reputation: 7839

The function sum returns a scalar, which is not what you want here. Instead, col1 + col2 + ... gives the desired result. So you can use Reduce in combination with +:

res$sum <- Reduce(`+`, res[, c('c1','c2','c3')])

The + operator must be quoted with backticks, since we are using it as a function. (I think quoting with normal quotation marks is OK too.)

rowSums also works, but my understanding is that it will create an intermediate matrix, which is not efficient.

Upvotes: 1

Konstantin Kotochigov
Konstantin Kotochigov

Reputation: 56

If I understood right what you need, just use rowSums() function.

res$sum <- rowSums(res[,2:4])

Upvotes: 2

Related Questions