[SOLVED] Remove and append middle column from a 3D numpy array

Issue

Suppose I have a 3D numpy array A, say given below:

A = np.array( [[[1,2,3], [4,5,6]] , [[7,8,9] , [10,11,12], [13,14,15]] ] , ndmin = 3 )

The only thing given about A is that it is a 3D arrays which is an array of arbitrary number of 2D arrays, where each 2D array is an array of arbitrary number of 1D arrays, and each 1D array has exactly 3 elements.

I want to remove the middle element from each 1D array from this 3D array, basically get the new array A1, and the removed column as X given below:

A1 = np.array( [[[1,3], [4,6]] , [[7,9] , [10,12], [13,15]] ] , ndmin = 3 )
X  = np.array( [ [[2],[5]], [[8],[11],[14]] ], ndmin = 3 )

I want to write a function that given A it outputs (A1, X) and another function which given (A1, X) outputs A. I believe it should be possible to write the first function via array slicing, but I am not able to do so. Also how do I write the second function.

Solution

For you ragged array, it is better to store in a list of np.arrays with shape n by 3:

A = [np.array([[1,2,3],
               [4,5,6]]) ,
     np.array([[7,8,9],
               [10,11,12],
               [13,14,15]])]

Now you could:

def remove_middle(arr):
    x = [a[:, 1] for a in arr]
    arr_new = [np.delete(a, 1, axis = 1) for a in arr]
    return arr_new, x

def insert_middle(arr, x):
    return [np.concatenate([a[:, :1], xx.reshape(-1, 1), a[:, 1:]], axis = 1) for a, xx in zip(arr, x)]
remove_middle(A)
([array([[1, 3],
         [4, 6]]),
  array([[ 7,  9],
         [10, 12],
         [13, 15]])],
 [array([2, 5]), array([ 8, 11, 14])])
insert_middle(*remove_middle(A))
# gets back the original A
[array([[1, 2, 3],
        [4, 5, 6]]),
 array([[ 7,  8,  9],
        [10, 11, 12],
        [13, 14, 15]])]

Answered By – Z Li

Answer Checked By – Cary Denson (BugsFixing Admin)

Leave a Reply

Your email address will not be published. Required fields are marked *