2009-01-22 2 views
4

скажем, у меня есть двумерный массив как этотудаления строк в Numpy массива на основе уникальности значения

numpy.array(
    [[0,1,1.2,3], 
    [1,5,3.2,4], 
    [3,4,2.8,4], 
    [2,6,2.3,5]]) 

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

array([0,1,1.2,3], 
     [3,4,2.8,4], 
     [2,6,2.3,5]) 

таким образом устраняя строки [1,5,3.2,4]

, который был бы лучшим способом сделать это?

ответ

1

Мой NumPy является выходом из практики, но это должно работать:

#keepers is a dictionary of type int: (int, int) 
#the key is the row's final value, and the tuple is (row index, row[2]) 
keepers = {} 
deletions = [] 
for i, row in enumerate(n): 
    key = row[3] 
    if key not in keepers: 
     keepers[key] = (i, row[2]) 
    else: 
     if row[2] > keepers[key][1]: 
      deletions.append(i) 
     else: 
      deletions.append(keepers[key][0]) 
      keepers[key] = (i, row[2]) 
o = numpy.delete(n, deletions, axis=0) 

Я значительно упрощен его от моего декларативного решения, которое получало довольно громоздким. Надеюсь, это легче будет следовать; все, что мы делаем, это поддерживать словарь значений, которые мы хотим сохранить, и список индексов, которые мы хотим удалить.

+0

Добавить в конце версию с 'itertools.groupby()' , Это интересно. – jfs

+0

, но это тоже неправильно ... – llimllib

+0

Я буду немного точнее: это неправильно алгоритмически. Чтобы работать, мне нужно было отсортировать массив, чего я действительно хочу избежать, чтобы сократить время выполнения до O (n), которое должно быть – llimllib

1

Это может быть достигнуто эффективно Numpy путем объединения lexsort и unique следующим

import numpy as np 

a = np.array([[0, 1, 1.2, 3], 
       [1, 5, 3.2, 4], 
       [3, 4, 2.8, 4], 
       [2, 6, 2.3, 5]]) 

# Sort by last column and 3rd column when values are equal 
j = np.lexsort(a.T) 

# Find first occurrence (=smallest 3rd column) of unique values in last column 
k = np.unique(a[j, -1], return_index=True)[1] 

print(a[j[k]]) 

Это возвращает желаемый результат

[[ 0. 1. 1.2 3. ] 
[ 3. 4. 2.8 4. ] 
[ 2. 6. 2.3 5. ]] 
Смежные вопросы