aura - 1 year ago 227
Python Question

# In Python 3, convert np.array object type to float type, with variable number of object element

I have a np.array with dtype as object. Each element here is a np.array with dtype as float and shape as (2,2) --- in maths, it is a 2-by-2 matrix. My aim is to obtain one 2-dimenional matrix by converting all the object-type element into float-type element. This can be better presented by the following example.

``````dA = 2  # dA is the dimension of the following A, here use 2 as example only
A = np.empty((dA,dA), dtype=object)  # A is a np.array with dtype as object
A[0,0] = np.array([[1,1],[1,1]])   # each element in A is a 2-by-2 matrix
A[0,1] = A[0,0]*2
A[1,0] = A[0,0]*3
A[1,1] = A[0,0]*4
``````

My aim is to have one matrix B (the dimension of B is 2*dA-by-2*dA). The form of B in maths should be

``````B =
1 1 2 2
1 1 2 2
3 3 4 4
3 3 4 4
``````

If dA is fixed at 2, then things can be easier, because I can hard-code

``````a00 = A[0,0]
a01 = A[0,1]
a10 = A[1,0]
a11 = A[1,1]
B0 = np.hstack((a00,a01))
B1 = np.hstack((a10,a11))
B = np.vstack((B0,B1))
``````

But in reality, dA is a variable, it can be 2 or any other integer. Then I don't know how to do it. I think nested for loops can help but maybe you have brilliant ideas. It would be great if there is something like cell2mat function in MATLAB. Because here you can see A[i,j] as a cell in MATLAB.

Here's a quick way.

Your `A`:

``````In [137]: A
Out[137]:
array([[array([[1, 1],
[1, 1]]), array([[2, 2],
[2, 2]])],
[array([[3, 3],
[3, 3]]), array([[4, 4],
[4, 4]])]], dtype=object)
``````

Use `numpy.bmat`, but convert `A` to a python list first, so `bmat` does what we want:

``````In [138]: B = np.bmat(A.tolist())

In [139]: B
Out[139]:
matrix([[1, 1, 2, 2],
[1, 1, 2, 2],
[3, 3, 4, 4],
[3, 3, 4, 4]])
``````

The result is actually a `numpy.matrix`. If you need a regular numpy array, use the `.A` attribute of the `matrix` object:

``````In [140]: B = np.bmat(A.tolist()).A

In [141]: B
Out[141]:
array([[1, 1, 2, 2],
[1, 1, 2, 2],
[3, 3, 4, 4],
[3, 3, 4, 4]])
``````

Here's an alternative. (It still uses `A.tolist()`.)

``````In [164]: np.swapaxes(A.tolist(), 1, 2).reshape(4, 4)
Out[164]:
array([[1, 1, 2, 2],
[1, 1, 2, 2],
[3, 3, 4, 4],
[3, 3, 4, 4]])
``````

In the general case, you would need something like:

``````In [165]: np.swapaxes(A.tolist(), 1, 2).reshape(A.shape[0]*dA, A.shape[1]*dA)
Out[165]:
array([[1, 1, 2, 2],
[1, 1, 2, 2],
[3, 3, 4, 4],
[3, 3, 4, 4]])
``````
Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download