Reputation: 3088
My data frame looks like this, but I have hundreds of columns
t1 <- c(11,2,3,4)
t2 <- c(10,2,3,4)
total1 <- c(8,2,3,4)
total2 <- c(4,6,3,4)
test <- data.frame(t1,t2,total1,total2)
t1 t2 total1 total2
1 11 10 8 4
2 2 2 2 6
3 3 3 3 3
4 4 4 4 4
I want to divide the t1/total2 and make a new column called freq1 and then t2/total2 and make a new column called freq2. I want to do this over hundreds of columns.
I want my data to look like this
t1 t2 total1 total2 freq1 freq2
1 11 10 8 4 1.37 2.5
2 2 2 2 6 1. 0.33
3 3 3 3 3. 1. 1
4 4 4 4 4. 1. 1
I am working like this
mutate(freq1= t1/total1)
But this is problematic. I can not do it for all columns.
Upvotes: 0
Views: 317
Reputation: 388982
Using dplyr
you can gather two groups of columns together and divide them, give new names to columns and bind it to original data.
library(dplyr)
bind_cols(test,
(test %>% select(matches('t\\d+'))/
test %>% select(matches('total\\d+'))) %>%
rename_with(~paste0('freq', seq_along(.)))
)
# t1 t2 total1 total2 freq1 freq2
#1 11 10 8 4 1.375 2.5000000
#2 2 2 2 6 1.000 0.3333333
#3 3 3 3 3 1.000 1.0000000
#4 4 4 4 4 1.000 1.0000000
Upvotes: 1
Reputation: 887108
We can subset the datasets for 't' columns and the 'total' separately and divide them (assuming they are in the same order)
test[paste0('freq', 1:2)] <- test[1:2]/test[3:4]
Upvotes: 1
Reputation: 1577
A nice Base R solution that doesn't even need regex is as follows
df <- sapply(1:(ncol(test)/2), function(x) test[,x]/test[,x+(ncol(test)/2)])
The idea is that you have a number of columns that divides 2, so you can just use sapply()
to divide a combination of columns.
Upvotes: 2
Reputation: 101335
Here is a base R option
cbind(
test,
lapply(
split.default(
test,
paste0("freq", gsub("\\D", "", names(test)))
),
Reduce,
f = "/"
)
)
which gives
t1 t2 total1 total2 freq1 freq2
1 11 10 8 4 1.375 2.5000000
2 2 2 2 6 1.000 0.3333333
3 3 3 3 3 1.000 1.0000000
4 4 4 4 4 1.000 1.0000000
Upvotes: 1