For an application, I have formulas defined in terms of a left Kronecker product of matrices, A,B, meaning A \otimes_L B = {A * B[i,j]} -- matrix on the left multiplies each element on the right. The standard kronecker() function is the right Kronecker product, A \otimes_R B = {A[i,j] * B} -- matrix on the right multiplies each element on the left. The example below shows the result of kronecker() and what I want, but kronecker() is now defined in generic S4 methods, and I can't see how to use more basic functions to get the result I want. Or, alternatively how to transform the result of kronecker() to give my wanted. ---- test code --- A <- matrix(1:4, 2,2, dimnames=list(c("a1", "a2"), c("a1","a2"))) B <- diag(2) dimnames(B) <- list(c("b1", "b2"), c("b1","b2")) # standard, right kronecker product: each A[i,j] * B kronecker(A, B, make.dimnames=TRUE) # left kronecker product: A * each B[i,j] wanted <- rbind( cbind(A * B[1,1], A*B[1,2]), cbind(A * B[2,1], A*B[2,2])) rownames(wanted) <- colnames(wanted) <- paste(rep(c("b1", "b2"), each=2), rownames(wanted), sep=":") wanted ---- R output ---- > A <- matrix(1:4, 2,2, dimnames=list(c("a1", "a2"), c("a1","a2"))) > B <- diag(2) > dimnames(B) <- list(c("b1", "b2"), c("b1","b2")) > # standard, right kronecker product: each A[i,j] * B > kronecker(A, B, make.dimnames=TRUE) a1:b1 a1:b2 a2:b1 a2:b2 a1:b1 1 0 3 0 a1:b2 0 1 0 3 a2:b1 2 0 4 0 a2:b2 0 2 0 4 > > # left kronecker product: A * each B[i,j] > wanted <- rbind( + cbind(A * B[1,1], A*B[1,2]), + cbind(A * B[2,1], A*B[2,2])) > > rownames(wanted) <- colnames(wanted) <- paste(rep(c("b1", "b2"), each=2), rownames(wanted), sep=":") > wanted b1:a1 b1:a2 b2:a1 b2:a2 b1:a1 1 3 0 0 b1:a2 2 4 0 0 b2:a1 0 0 1 3 b2:a2 0 0 2 4 > -- Michael Friendly Email: friendly AT yorku DOT ca Professor, Psychology Dept. & Chair, Quantitative Methods York University Voice: 416 736-2100 x66249 Fax: 416 736-5814 4700 Keele Street Web: http://www.datavis.ca Toronto, ONT M3J 1P3 CANADA
On 23-02-2013, at 20:46, Michael Friendly <friendly at yorku.ca> wrote:> For an application, I have formulas defined in terms of a left Kronecker product of matrices, > A,B, meaning > A \otimes_L B = {A * B[i,j]} -- matrix on the left multiplies each element on the right. > > The standard kronecker() function is the right Kronecker product, > A \otimes_R B = {A[i,j] * B} -- matrix on the right multiplies each element on the left. > > The example below shows the result of kronecker() and what I want, but > kronecker() is now defined in generic S4 methods, and I can't see > how to use more basic functions to get the result I want. Or, alternatively > how to transform the result of kronecker() to give my wanted. > > ---- test code --- > A <- matrix(1:4, 2,2, dimnames=list(c("a1", "a2"), c("a1","a2"))) > B <- diag(2) > dimnames(B) <- list(c("b1", "b2"), c("b1","b2")) > # standard, right kronecker product: each A[i,j] * B > kronecker(A, B, make.dimnames=TRUE) > > # left kronecker product: A * each B[i,j] > wanted <- rbind( > cbind(A * B[1,1], A*B[1,2]), > cbind(A * B[2,1], A*B[2,2])) > rownames(wanted) <- colnames(wanted) <- paste(rep(c("b1", "b2"), each=2), rownames(wanted), sep=":") > wanted > > ---- R output ---- > > A <- matrix(1:4, 2,2, dimnames=list(c("a1", "a2"), c("a1","a2"))) > > B <- diag(2) > > dimnames(B) <- list(c("b1", "b2"), c("b1","b2")) > > # standard, right kronecker product: each A[i,j] * B > > kronecker(A, B, make.dimnames=TRUE) > a1:b1 a1:b2 a2:b1 a2:b2 > a1:b1 1 0 3 0 > a1:b2 0 1 0 3 > a2:b1 2 0 4 0 > a2:b2 0 2 0 4 > > > > # left kronecker product: A * each B[i,j] > > wanted <- rbind( > + cbind(A * B[1,1], A*B[1,2]), > + cbind(A * B[2,1], A*B[2,2])) > > > > rownames(wanted) <- colnames(wanted) <- paste(rep(c("b1", "b2"), each=2), rownames(wanted), sep=":") > > wanted > b1:a1 b1:a2 b2:a1 b2:a2 > b1:a1 1 3 0 0 > b1:a2 2 4 0 0 > b2:a1 0 0 1 3 > b2:a2 0 0 2 4 > >How about kronecker(B, A, make.dimnames=TRUE) Berend