2016-07-13 2 views
2

Я хотел бы выбрать каждую n-ю группу из n столбцов в массиве numpy. Это означает, что я хочу первые п столбцов, а не п следующие столбцы, п следующие столбцы, а не п следующие столбцы и т.д.Выбор каждой альтернативной группы из n столбцов - NumPy

Например, с помощью следующего массива и n=2:

import numpy as np 
arr = np.array([[1, 2, 3, 4, 5, 6, 7, 8, 9, 10], 
       [11, 12, 13, 14, 15, 16, 17, 18, 19, 20]]) 

I хотели бы получить:

[[1, 2, 5, 6, 9, 10], 
[11, 12, 15, 16, 19, 20]] 

И с n=3:

[[1, 2, 3, 7, 8, 9], 
[11, 12, 13, 17, 18, 19]] 

С n=1 мы можем просто использовать синтаксис arr[:,::2], но есть ли что-то подобное для n>1?

ответ

3

Вы можете использовать modulus для создания рампы, начиная с 0 до 2n, а затем выберите первый n из каждой такой рампы. Таким образом, для каждого рампы мы бы сначала установили n как True и останемся как False, чтобы дать нам булевский массив, охватывающий всю длину массива. Затем мы просто используем boolean indexing по столбцам, чтобы выбрать допустимые столбцы для окончательного вывода. Таким образом, реализация будет выглядеть примерно так -

arr[:,np.mod(np.arange(arr.shape[-1]),2*n)<n] 

Шаг за шагом код работает, чтобы дать лучшее представление -

In [43]: arr 
Out[43]: 
array([[ 1, 2, 3, 4, 5, 6, 7, 8, 9, 10], 
     [11, 12, 13, 14, 15, 16, 17, 18, 19, 20]]) 

In [44]: n = 3 

In [45]: np.mod(np.arange(arr.shape[-1]),2*n) 
Out[45]: array([0, 1, 2, 3, 4, 5, 0, 1, 2, 3]) 

In [46]: np.mod(np.arange(arr.shape[-1]),2*n)<n 
Out[46]: array([ True,True,True,False,False,False,True,True,True,False]) 

In [47]: arr[:,np.mod(np.arange(arr.shape[-1]),2*n)<n] 
Out[47]: 
array([[ 1, 2, 3, 7, 8, 9], 
     [11, 12, 13, 17, 18, 19]]) 

образец проходит через различные n -

In [29]: arr 
Out[29]: 
array([[ 1, 2, 3, 4, 5, 6, 7, 8, 9, 10], 
     [11, 12, 13, 14, 15, 16, 17, 18, 19, 20]]) 

In [30]: n = 1 

In [31]: arr[:,np.mod(np.arange(arr.shape[-1]),2*n)<n] 
Out[31]: 
array([[ 1, 3, 5, 7, 9], 
     [11, 13, 15, 17, 19]]) 

In [32]: n = 2 

In [33]: arr[:,np.mod(np.arange(arr.shape[-1]),2*n)<n] 
Out[33]: 
array([[ 1, 2, 5, 6, 9, 10], 
     [11, 12, 15, 16, 19, 20]]) 

In [34]: n = 3 

In [35]: arr[:,np.mod(np.arange(arr.shape[-1]),2*n)<n] 
Out[35]: 
array([[ 1, 2, 3, 7, 8, 9], 
     [11, 12, 13, 17, 18, 19]]) 
+0

Спасибо! Просто вопрос, есть ли конкретная причина, почему вы используете 'arr.shape [-1]', а не 'arr.shape [1]'? –

+0

@ Jean-BaptisteMartin Я предполагаю, что у меня был общий ndarray, так что он будет работать для массивов любых измерений для выбора столбцов, которые всегда будут последним измерением. – Divakar

+1

Возможно, стоит отметить, что это и практически любой другой способ достижения желаемого результата создает новый массив (копирует данные), а не вид исходного массива. – Dunes

Смежные вопросы