Numpy: argsort дает неправильные результаты

Созданный на 8 мар. 2017  ·  4Комментарии  ·  Источник: numpy/numpy

Функция argsort кажется сломанной. Глядя на предоставленный код, сортировка аргументов для строк [0, 1] верна, но она испорчена для строк [2, 3].
Я тестировал это на разных установках NumPy и версиях 1.11.0 и 1.12.0.

import numpy as np

vec = np.array([
    [-1.4, -1.2,  1.3],
    [-3.6,  3.9, -3.7],
    [-2.3,  1.5, -2. ],
    [-2.6,  2.4, -1.6]
    ])

In [1]: np.argsort(-vec, axis=1)
Out[1]: 
array([[2, 1, 0],
       [1, 0, 2],
       [1, 2, 0],
       [1, 2, 0]])
53 - Invalid

Самый полезный комментарий

Это второй результат Google для «неправильный np argsort».

Объяснение на странице документов непонятно (мне). Я добавлю свое собственное объяснение здесь в надежде, что оно кому-то поможет:

x = numpy.array([1.48,1.31,0.0,0.8])
print x.argsort()

>[2 3 1 0]

Некоторые люди могут ожидать , что это вместо этого даст [3, 2, 0, 1] , т. е. 0-й элемент в несортированном массиве должен быть 3-м элементом в отсортированном массиве.

На самом деле он предоставляет такие индексы, что x[np.argsort(x)] даст вам отсортированный список, т.е. [0.0, 0.8, 1.31, 1.48] . Иными словами, [2 3 1 0] говорит вам, что 0-й элемент отсортированного массива является 2-м элементом несортированного массива.

Если вы действительно хотите получить [3, 2, 0, 1] в качестве вывода, вы можете вместо этого сделать

np.argsort(np.argsort(x))
>[3 2 0 1]

В качестве альтернативы, если вы просто действительно нестандартны, как я, и хотите, скажем, только индексы 3 самых больших элементов в x :

np.argsort(x)[:-4:-1]
>[0, 1, 3]

Все 4 Комментарий

Не вижу ничего плохого в результате, распечатайте vec[np.arange(4)[:, np.newaxis], np.argsort(-vec, axis=1)] и убедитесь, что он выглядит хорошо.

Это второй результат Google для «неправильный np argsort».

Объяснение на странице документов непонятно (мне). Я добавлю свое собственное объяснение здесь в надежде, что оно кому-то поможет:

x = numpy.array([1.48,1.31,0.0,0.8])
print x.argsort()

>[2 3 1 0]

Некоторые люди могут ожидать , что это вместо этого даст [3, 2, 0, 1] , т. е. 0-й элемент в несортированном массиве должен быть 3-м элементом в отсортированном массиве.

На самом деле он предоставляет такие индексы, что x[np.argsort(x)] даст вам отсортированный список, т.е. [0.0, 0.8, 1.31, 1.48] . Иными словами, [2 3 1 0] говорит вам, что 0-й элемент отсортированного массива является 2-м элементом несортированного массива.

Если вы действительно хотите получить [3, 2, 0, 1] в качестве вывода, вы можете вместо этого сделать

np.argsort(np.argsort(x))
>[3 2 0 1]

В качестве альтернативы, если вы просто действительно нестандартны, как я, и хотите, скажем, только индексы 3 самых больших элементов в x :

np.argsort(x)[:-4:-1]
>[0, 1, 3]

Если вы действительно хотите получить [3, 2, 0, 1] в качестве вывода, вы можете вместо этого сделать

Это будет быстрее:

a = np.empty(len(x), np.intp)
a[np.argsort(x)] = np.arange(len(x))

9880 предлагает добавить это в numpy как np.invert_permutation(np.argsort(x))

@rossbar , @bjnath : Возможно, стоит извлечь материал из комментария @ghost выше и поместить его в документы? Я добавил еще несколько перекрестных ссылок, чтобы показать больше примеров путаницы.

Была ли эта страница полезной?
0 / 5 - 0 рейтинги

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

inducer picture inducer  ·  3Комментарии

qualiaa picture qualiaa  ·  3Комментарии

'
Pezhvuk picture Pezhvuk  ·  4Комментарии

Levstyle picture Levstyle  ·  3Комментарии

manuels picture manuels  ·  3Комментарии