Effectively create a matrix of function values

For experienced R developers to consider the most efficient (but still readable) way to build a matrix with a given number of rows and columns from a given function, for example, A_ij = someFun (i, j) with 1 <= i <= rows, 1 <= j <= cols?

Since I could not find something in the documentation, I came up with

initMatrix <- function(rows, cols, fn) { A <- matrix(nrow=rows, ncol=cols) for (i in 1:rows) for (j in 1:cols) A[i,j] <- fn(i,j) return(A) } 

which seems stupid and slow for me. Any improvements (especially single-line) are welcome! :)

+6
source share
3 answers

I think you are looking for outer(seq(rows),seq(cols),fn) (or, as suggested below, outer(seq_len(rows),seq_len(cols),fn) : some examples are needed to see how many a distinction has been made).

You can get a lot of readability (at least if you don’t need to look for ?outer to find out what is going on) this way, but I really don’t think you will save a lot of time. Maybe something smarter and more efficient if your fn vectorized to begin with: is it?

+7
source

look outer :

 > outer (LETTERS [1:3], letters [4:7], paste) [,1] [,2] [,3] [,4] [1,] "A d" "A e" "A f" "A g" [2,] "B d" "B e" "B f" "B g" [3,] "C d" "C e" "C f" "C g" 
+6
source

If you simply write a function, you may get errors that cause "external", so insert text in it first.

 fn <- function(i,j){ ... } A <- outer(1:rows, 1:cols, Vectorize(fn)) 

An example where it will not work without Vectorizing:

 fn <- function(i,j){ return(prop.test(c(tables[i,1], tables[j,1]), c(sum(tables[i,]), sum(tables[j,])))$p.value) } 
+1
source

Source: https://habr.com/ru/post/900287/


All Articles