Увеличение скорости поиска индекса предмета в списке - PullRequest
1 голос
/ 30 марта 2019

Я пытаюсь ускорить программу, которую я написал, и после импорта cProfile я вижу, что одна функция отнимает огромное количество времени на вычисления.

Это то, что находит numpy.ndarray в списке:

    def locate(arr, l ):
        for i in range(len(l)):
            if np.all(l[i] == arr):
                return i
        return -1

Поскольку список нельзя упорядочить и т. Д., Я не вижу способа избежать сканирования всего списка. Я прочитал несколько статей о векторизации и хотел знать, можно ли это применить здесь или есть какой-то другой способ ускорить это?

Спасибо

Ответы [ 4 ]

2 голосов
/ 30 марта 2019

Вы, вероятно, не можете избежать просмотра списка, но вы можете ускорить сравнение:

Пример настройки:

L  = list(np.floor(np.outer(*2*(np.linspace(1,10,1000),))))
arr = L[537]

Прямой метод для справки:

import itertools as it

next(it.chain((i for i, a in enumerate(L) if np.all(arr==a)), (-1,)))
# 537
timeit(lambda: next(it.chain((i for i, a in enumerate(L) if np.all(arr==a)), (-1,))), number=100)
# 0.27100146701559424

Подход 1: Используйте np.array_equal (медленнее)

next(it.chain((i for i, a in enumerate(L) if np.array_equal(arr, a)), (-1,)))
# 537
timeit(lambda: next(it.chain((i for i, a in enumerate(L) if np.array_equal(arr, a)), (-1,))), number=100)
# 0.2992244770284742

Подход 2. Использование пустого вида (быстрее)

arr_v = arr.reshape(-1).view(f'V{arr.itemsize*arr.size}')

next(it.chain((i for i, a in enumerate(L) if arr_v==a.reshape(-1).view(f'V{a.itemsize*a.size}')), (-1,)))
# 537
timeit(lambda: next(it.chain((i for i, a in enumerate(L) if arr_v==a.reshape(-1).view(f'V{a.itemsize*a.size}')), (-1,))), number=100)
# 0.11853155982680619
1 голос
/ 30 марта 2019

Существует встроенная функция python, называемая index(), где вы можете использовать ее, подключив строку в качестве значения и найдя ее индекс в списке.

0 голосов
/ 30 марта 2019
0 голосов
/ 30 марта 2019

Так вы ищете np.where

temp_list=np.array(temp_list)
np.where(temp_list==5)
(array([1, 3, 6, 8]),)
...