Numpy добавление и нормальное добавление

1
x = [[1,2],[2,3],[10,1],[10,10]]

def duplicatingRows(x, l):
    severity = x[l][1]
    if severity == 1 or severity == 2:
        for k in range(1,6):
            x.append(x[l])

for l in range(len(x)):
    duplicatingRows(x,l)

print(x)            

x = np.array([[1,2],[2,3],[10,1],[10,10]])

def duplicatingRows(x, l):
    severity = x[l][1]
    if severity == 1 or severity == 2:
        for k in range(1,6):
            x = np.append(x, x[l])

for l in range(len(x)):
    duplicatingRows(x,l)

print(x)

Я бы хотел, чтобы он печатал массив с дополнительными добавленными строками. Выделение списка [[1, 2], [2, 3], [10, 1], [10, 10], [1, 2], [1, 2], [1, 2], [1, 2], [1, 2], [10, 1], [10, 1], [10, 1], [10, 1], [10, 1]]. Почему это не работает? Я также пробовал различные комбинации с конкатенатом, но он не работал.

  • 1
    Не пытайтесь использовать np.append. Это того не стоит.
Теги:
numpy
list
atom-editor
append

2 ответа

1

У вас есть некоторые ошибки в коде. Здесь немного улучшена, правильная и (частично) векторная реализация вашего кода, который печатает ваш желаемый результат.

Здесь мы используем numpy.tile для повторения строк, за которым следует изменение, чтобы мы могли добавить его вдоль оси 0, что и является необходимым.

In [24]: x = np.array([[1,2],[2,3],[10,1],[10,10]]) 

         def duplicatingRows(x, l): 
             severity = x[l][1] 
             if severity == 1 or severity == 2:
                 # replaced your 'for' loop
                 # 5 corresponds to 'range(1, 6)'
                 reps = np.tile(x[l], 5).reshape(5, -1) 
                 x = np.append(x, reps, axis=0) 
             return x 

         for l in range(len(x)): 
             x = duplicatingRows(x,l) 

         print(x)

Выход:

[[ 1  2]
 [ 2  3]
 [10  1]
 [10 10]
 [ 1  2]
 [ 1  2]
 [ 1  2]
 [ 1  2]
 [ 1  2]
 [10  1]
 [10  1]
 [10  1]
 [10  1]
 [10  1]]
0

Возьмем подход с целым массивом

In [140]: arr = np.array([[1,2],[2,3],[10,1],[10,10]])
In [141]: arr
Out[141]: 
array([[ 1,  2],
       [ 2,  3],
       [10,  1],
       [10, 10]])

Мы хотим реплицировать строки, где 2-й столбец имеет 1 или 2, правильно? isin делает приятную "маску" (мы также можем использовать == и any):

In [142]: np.isin(arr[:,1],[1,2])
Out[142]: array([ True, False,  True, False])
In [143]: torepeat = arr[np.isin(arr[:,1],[1,2])]
In [144]: torepeat
Out[144]: 
array([[ 1,  2],
       [10,  1]])

np.repeat делает хорошую работу по репликации значений, которые мы можем просто объединить с оригиналом:

In [145]: repeated = np.repeat(torepeat,5, axis=0)
In [146]: np.concatenate((arr, repeated),axis=0)
Out[146]: 
array([[ 1,  2],
       [ 2,  3],
       [10,  1],
       [10, 10],
       [ 1,  2],
       [ 1,  2],
       [ 1,  2],
       [ 1,  2],
       [ 1,  2],
       [10,  1],
       [10,  1],
       [10,  1],
       [10,  1],
       [10,  1]])

np.append использует concatenate. Он работает нормально с добавлением одного элемента в 1d-массив, но становится более сложным для использования с более высокими измерениями. Это плохое подражание списку. Также повторяющиеся конкатенации в петле относительно медленны. Обычно мы рекомендуем список добавления, с одной строкой массива в конце.

Другой способ repeat итеративно:

In [164]: np.concatenate([np.repeat(a[None,:], 5, axis=0) for a in arr if (a[1]==1 or a[1]==2)], axis=0)
Out[164]: 
array([[ 1,  2],
       [ 1,  2],
       [ 1,  2],
       [ 1,  2],
       [ 1,  2],
       [10,  1],
       [10,  1],
       [10,  1],
       [10,  1],
       [10,  1]])

Ещё вопросы

Сообщество Overcoder
Наверх
Меню