Home > Software design >  Cross products of each row of a matrix with the corresponding row of another matrix
Cross products of each row of a matrix with the corresponding row of another matrix

Time:11-13

Suppose I have the following 2 matrices

A <- matrix(nrow = 5, ncol = 3, byrow = TRUE, c(
  5, 1, 2, 
  3, 1, 5, 
  5, 1, 3, 
  7, 2, 8, 
  2, 4, 2
))

B <- matrix(nrow = 5, ncol = 2, byrow = TRUE, c(
  2, 1,
  3, 5,
  1, 4,
  3, 3,
  3, 4
))

and I want to create an array

arr <- array(NA, dim = c(ncol(A), ncol(B), nrow(A))) 

to store the cross product of row i of matrix A with the same row i of matrix B. For example, slice 2 of arr would be

A[2, ] %*% t(B[2, ]

     [,1] [,2]
[1,]    9   15
[2,]    3    5
[3,]   15   25

Using a for loop, I can do

for (i in 1:nrow(A)) {
  arr[, , i] <- A[i, ] %*% t(B[i, ])
}

Or using an sapply function

temp <- sapply(1:nrow(A), function(i) A[i, ] %*% t(B[i, ]), simplify = FALSE)

arr <- array(unlist(temp), dim = c(ncol(A), ncol(B), nrow(A))) 

I am wondering if there is more clever way using matrix products or built-in functions in this case. Thank you so much.

CodePudding user response:

Using einstein summation notation

library(einsum)

arr2 <- einsum("ij,ik->jki", A, B)
identical(arr2, arr)
## [1] TRUE

CodePudding user response:

We can try base R option with mapply tcrossprod like below

array(
  mapply(tcrossprod, asplit(A, 1), asplit(B, 1)),
  c(ncol(A), ncol(B), nrow(A))
)
  • Related