'use map2 to multiply more than two lists of matrices in R

I have

A = list(a = matrix(1:4, 2), b = matrix(2:5, 2))

G = list(a = matrix(10:13, 2), b = matrix(25:28, 2))

columns <- list(a = matrix(3:4, 1), b = matrix(1:2, 1))

I want to make another list of cross-products of all the elements with the same name across lists, so I do purrr::map2(A, G, columns, `%*%`). It doesn't look like map2 allows more than two elements. Is there a workaround?

Error in `stop_bad_length()`:
! Index 1 must have length 1, not 2
Backtrace:
 1. purrr::map2(A, G, columns, `%*%`)
 4. purrr:::stop_bad_element_length(...)
 5. purrr:::stop_bad_length(...)

I also tried purrr::pmap(list(A, G, columns), %*%), but no luck.

purrr::map2(A, G, `%*%`) works beautifully.



Solution 1:[1]

Similar to @Cettt's approach in tidyverse - where we take in list in pmap, and then reduce with %*%. Note that the the 'columns' elements needs to be transposed

library(purrr)
pmap(list(A, G, columns), ~ reduce(list(..1, ..2, t(..3)), `%*%`))
$a
     [,1]
[1,]  333
[2,]  496

$b
     [,1]
[1,]  486
[2,]  647

Or an option with Map from base R

Map(\(x, y, z) Reduce(`%*%`, list(x, y, t(z))), A, G, columns)
$a
     [,1]
[1,]  333
[2,]  496

$b
     [,1]
[1,]  486
[2,]  647

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 akrun