Более питонический способ перебора объема в произвольной оси? - PullRequest
1 голос
/ 25 сентября 2019

У меня есть функция, которая берет трехмерный массив (который мы назовем томом) и преобразует его в список 2D-срезов.Я хочу, чтобы пользователь мог указать ось, по которой он разрезан.Я управляю этим с помощью приведенного ниже кода, но тройное выражение if не кажется самым элегантным способом сделать это.Буду признателен людям за мысли о том, можно ли добиться этого лучше.

axis = 0 # Can be set to 0, 1, or 2 

volume = np.ones((100, 100, 100))

n_slices = volume.shape[axis]

slices = []

for i in range(n_slices):

    if axis == 0:
        my_slice = volume[i, :, :]
    elif axis == 1:
        my_slice = volume[:, i, :]
    elif axis == 2:
        my_slice = volume[:, :, i]

    slices.append(my_slice)

Ответы [ 3 ]

3 голосов
/ 25 сентября 2019

Просто используйте np.moveaxis -

slices_ar = np.moveaxis(volume,axis,0)

Самое приятное то, что это просмотр ввода и, следовательно, практически свободный во время выполнения.Давайте проверим view-part -

In [83]: np.shares_memory(volume, np.moveaxis(volume,axis,0))
Out[83]: True

В качестве альтернативы, используйте np.rollaxis, который делает то же самое -

np.rollaxis(volume,axis,0)
1 голос
/ 25 сентября 2019

Вы можете использовать

my_slice = volume[tuple(i if n == axis else slice(100) for n in range(3))]

, чтобы

slices = [volume[tuple(i if n == axis else slice(100) for n in range(3))] for i in range(100)]
1 голос
/ 25 сентября 2019

Я думаю, что вы хотите [numpy.split ()]: (https://docs.scipy.org/doc/numpy/reference/generated/numpy.split.html)

axis = 0 # Can be set to 0, 1, or 2 
volume = np.ones((100, 100, 100))
n_slices = volume.shape[axis]

slices = np.split(volume, n_slices, axis)
...