Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Iterate over columns of a matrix in R

Tags:

r

matrix

I have a function

function (x, y) { ... }

which expects two vectors x and y and returns a value calculated from them.

I want to apply this function pairwise to the column vectors of two matrices xs and ys. From R, iterating over the row vectors of a matrix I found mapply() but this seems to apply the function pairwise to each element of the matrix. Instead, I want to apply the function to an entire column. How do I do this?

For clarification, here's a contrived example:

xs <- matrix(c(1, 2, 3, 4, 5, 6), nrow = 3, ncol = 2)
ys <- matrix(c(25, 26, 27, 28, 29, 30), nrow = 3, ncol = 2)
dot <- function(x, y) sum(x*y)
like image 394
Code-Apprentice Avatar asked Sep 20 '19 16:09

Code-Apprentice


3 Answers

Nobody yet mentioned asplit (added in R 3.6.0) - the function made specifically for this case.

Example:

mapply(dot, asplit(xs, 2), asplit(ys, 2))

Same but using rows:

mapply(dot, asplit(xs, 1), asplit(ys, 1))
like image 134
Karolis Koncevičius Avatar answered Nov 11 '22 23:11

Karolis Koncevičius


Here is one way:

xs <- matrix(c(1, 2, 3, 4, 5, 6), nrow = 3, ncol = 2)
ys <- matrix(c(25, 26, 27, 28, 29, 30), nrow = 3, ncol = 2)
dot <- function(x, y) {
  sum(x*y)
}

dots <- sapply(1:ncol(xs),function(i) dot(xs[,i],ys[,i])) #dots = c(158, 437)
like image 39
John Coleman Avatar answered Nov 11 '22 23:11

John Coleman


Using a simple for loop

v1 <- numeric(ncol(xs))
for(i in seq_along(v1)) v1[i] <- dot(xs[,i], ys[,i])
v1
#[1] 158 437

Or with vectorized option

colSums(xs * ys)
#[1] 158 437
like image 29
akrun Avatar answered Nov 11 '22 23:11

akrun