Reputation: 13903
I'm evaluating this formula (from Székely and Rizzo, 2013, page 1263), in which a
and b
are symmetric, n
-by-n
matrices.
How can I vectorize the section with the nested for
loop? I feel like there are probably clever matrix manipulation tricks that I could use here, maybe along with the sweep
function.
Here is what I have now:
u_squared <- function(a, b, n) {
a. <- .colSums(a, n, n)
b. <- .colSums(b, n, n)
a.. <- sum(a.)
b.. <- sum(b.)
u1 <- 0
u2 <- 0
u3 <- 0
for (i in 1:n) {
for (j in 1:n) {
u1 <- u1 + a[i, j] * b[i, j]
u2 <- u2 + a[i, j] * (b.. - 2*b.[j] - 2*b.[i] + 2*b[i, j])
u3 <- u3 + a[i, j] * (b.[i] - b[i, j])
}
}
u1 <- u1 / (n * (n-1))
u2 <- u2 / (n * (n-1) * (n-2) * (n-3))
u3 <- u3 / (n * (n-1) * (n-2))
return (u1 + u2 - 2 * u3)
}
For instance, I know that u1
could be computed simply as u1 <- a * b
but I wanted to unroll the entire formula just to demonstrate the underlying math. What I'm looking for are similar vectorizations for u2
and u3
.
Upvotes: 0
Views: 274
Reputation: 7373
It can be easily vectorized
u_squared1 <- function(a, b, n){
b. <- matrix(.colSums(b, n, n), n, n)
B1 <- b.. - 2 * b. - 2 * t(b.) + 2*b
B2 <- b. - b
u1 <- sum(a*b) / (n * (n-1))
u2 <- sum(a*B1) / (n * (n-1) * (n-2) * (n-3))
u3 <- sum(a*B2) / (n * (n-1) * (n-2))
return (u1 + u2 - 2 * u3)
}
Upvotes: 4