Reputation: 203
I have three Numpy matrices
a = np.matrix('1 2; 3 4')
b = np.matrix('5 6 7; 8 9 10')
c = np.matrix('1 2 3; 4 5 6; 7 8 9')
and I would like to make the following block matrix:
M = [a b ; 0 c]
,
where 0
stands for a matrix of zeros with the relevant dimensions.
Upvotes: 5
Views: 4447
Reputation: 1
My method to generate and join block-wise matrix:
def blockwise(matrix, block=(3, 3)):
shape = (int(matrix.shape[0] / block[0]), int(matrix.shape[1] / block[1])) + block
strides = (matrix.strides[0] * block[0], matrix.strides[1] * block[1]) + matrix.strides
return as_strided(matrix, shape=shape, strides=strides)
def block_join(blocks):
return np.vstack(map(np.hstack, blocks))
arr = np.arange(36).reshape((6, 6))
blocks = blockwise(arr, (3, 3))
print(blocks)
re_join = block_join(blocks)
print(re_join)
then the output is as following:
>>>>[[[[ 0 1 2]
[ 6 7 8]
[12 13 14]]
[[ 3 4 5]
[ 9 10 11]
[15 16 17]]]
[[[18 19 20]
[24 25 26]
[30 31 32]]
[[21 22 23]
[27 28 29]
[33 34 35]]]]
[[ 0 1 2 3 4 5]
[ 6 7 8 9 10 11]
[12 13 14 15 16 17]
[18 19 20 21 22 23]
[24 25 26 27 28 29]
[30 31 32 33 34 35]]
Upvotes: 0
Reputation: 22902
An easy way to create a block matrix is numpy.bmat
(as pointed out by @inquisitiveIdiot). Judging by the block matrix you're looking to create, you need a 3x2 matrix of zeros:
>>> import numpy as np
>>> z = np.zeros( (3, 2) )
You can then create a block matrix by passing a 2x2 array of the blocks to numpy.bmat
:
>>> M = np.bmat( [[a, b], [z, c]] )
>>> M
matrix([[ 1., 2., 5., 6., 7.],
[ 3., 4., 8., 9., 10.],
[ 0., 0., 1., 2., 3.],
[ 0., 0., 4., 5., 6.],
[ 0., 0., 7., 8., 9.]])
Another (IMO more complicated) method is to use numpy.hstack
and numpy.vstack
.
>>> M = np.vstack( (np.hstack((a, b)), np.hstack((z, c))) )
>>> M
matrix([[ 1., 2., 5., 6., 7.],
[ 3., 4., 8., 9., 10.],
[ 0., 0., 1., 2., 3.],
[ 0., 0., 4., 5., 6.],
[ 0., 0., 7., 8., 9.]])
Upvotes: 8