Лучший способ вставить элементы в массив NumPy - PullRequest
0 голосов
/ 15 сентября 2018

У меня есть пустой массив, и у меня есть список элементов, которые я хочу вставить в определенные места (не смежные) в этот массив.Индексы находятся в другом массиве.

target answer: [1,2,3,4,5]
original array: [1,3,5]
elements to insert: [2,4]
indices: [1,3]

numpy.insert(arr,[1,3],[2,4]) не дают желаемого результата.Это дает [1,2,3,5,4].Есть указатели?

Ответы [ 2 ]

0 голосов
/ 15 сентября 2018

Список подходов:

In [122]: alist=[1,3,5]
In [123]: for i,j in zip([1,3],[2,4]):
     ...:     alist[i:i] = [j]
     ...:     
In [124]: alist
Out[124]: [1, 2, 3, 4, 5]

np.insert - это сложная функция, использующая разные подходы в зависимости от ввода индексов.Но в таком случае используется подход логической маски:

In [126]: arr = np.array([1,3,5])
In [127]: res = np.zeros(5, int) # 5 is len(arr)+len([2,4])
In [128]: mask = res.astype(bool)
In [129]: mask[[1,3]] = True
In [130]: mask
Out[130]: array([False,  True, False,  True, False])
In [131]: res[mask] = [2,4]
In [132]: res[~mask] = arr
In [133]: res
Out[133]: array([1, 2, 3, 4, 5])

mask определяет, куда должны идти новые значения, и ~mask, куда идут оригиналы.

insert предполагает, что индексы даны относительно исходного массива, а не цели.Чтобы сделать то же самое, ему нужно дать [1,2], другими словами после arr[1] и arr[2].insert настроит [1,2] на [1,3] для использования вышеуказанного подхода маскирования.@ Ответ Дивакара берет ваш [1,3] и преобразует его в [1,2], которого ожидает insert.По сути, он компенсирует смещение, которое обычно добавляет insert.


Если мы использовали [1,2] (индексы относительно списка источников), итерация списка, которую я использовал выше, неверна.Он не учитывает тот факт, что список увеличивается после вставки 2:

In [134]: alist=[1,3,5]
In [135]: for i,j in zip([1,2],[2,4]):
     ...:     alist[i:i] = [j]   
In [136]: alist
Out[136]: [1, 2, 4, 3, 5]

Чтобы компенсировать это, обычная хитрость заключается в вставке в обратном порядке:

In [137]: alist=[1,3,5]
In [138]: for i,j in zip([1,2][::-1],[2,4][::-1]):
     ...:     alist[i:i] = [j]
In [139]: alist
Out[139]: [1, 2, 3, 4, 5]
0 голосов
/ 15 сентября 2018

Использовать индексы со смещением диапазона с np.insert -

np.insert(a, add_idx - np.arange(len(add_idx)), add_val)

Пробный прогон -

In [20]: a
Out[20]: array([1, 3, 5])

In [21]: add_idx
Out[21]: [1, 3]

In [22]: add_val
Out[22]: [2, 4]

In [23]: np.insert(a, add_idx - np.arange(len(add_idx)), add_val)
Out[23]: array([1, 2, 3, 4, 5])
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...