Количество элементов массивов numpy внутри конкретных бинов - PullRequest
0 голосов
/ 16 мая 2018

У меня есть ансамбль из отсортированных (одномерных) массивов неравной длины (скажем, M0, M1 и M2). Я хочу найти , сколько элементов каждого из этих массивов находится в определенных диапазонах чисел (где диапазоны номеров определены соседними элементами из другого отсортированного массива , скажем zbin). Я хочу знать, что является самым быстрым способом для достижения этой цели.

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

""" Function to do search query """
def search(numrange, lst):
    arr = np.zeros(len(lst))        
    for i in range(len(lst)):
        probe = lst[i]
        count = 0
        for j in range(len(probe)):
            if (probe[j]>numrange[1]): break
            if (probe[j]>=numrange[0]) and (probe[j]<=numrange[1]): count = count + 1   

        arr[i] = count
    return arr


""" Some example of sorted one-dimensional arrays of unequal lengths """
M0 = np.array([5.1, 5.4, 6.4, 6.8, 7.9])
M1 = np.array([5.2, 5.7, 8.8, 8.9, 9.1, 9.2])
M2 = np.array([6.1, 6.2, 6.5, 7.2])

""" Implementation and output """
lst = [M0, M1, M2]
zbin = np.array([5.0, 5.5, 6.0, 6.5])
zarr = np.zeros( (len(zbin)-1, len(lst)) )
for i in range(len(zbin)-1):
    numrange = [zbin[i], zbin[i+1]]
    zarr[i,:] = search(numrange, lst)

print zarr

Выход:

[[ 2.  1.  0.]
 [ 0.  1.  0.]
 [ 1.  0.  3.]] 

Здесь конечный результат zarr дает мне количество элементов каждого из массивов (M0, M1 и M2) внутри каждого из ящиков, возможное от zbin (, а именно . [5.0, 5.5], [5.5, 6.0] и [6.0, 6.5].) Например, рассмотрим корзину [5.0, 5.5]. Массив M0 содержит 2 элементов внутри этого бункера (5.1 и 5.4), M1 имеет 1 элемент (5.2) и M2 имеет 0 элементов в этой корзине. Это дает первый ряд zarr, т.е. [2,1,0]. Можно получить другие строки zarr аналогичным образом.

В моей реальной задаче я буду иметь дело с zbin длин, намного превышающих то, что я дал в этом примере, а также с большими и многими другими массивами, такими как M0, M1, ... Mn. Все M s и массив zbin будут отсортированы всегда. Мне интересно, являются ли разработанная мной функция (search()) и метод, которым я следую, являются наиболее оптимальными и самыми быстрыми способами для достижения желаемой функциональности. Я буду очень признателен за любую помощь.

Ответы [ 2 ]

0 голосов
/ 16 мая 2018

Мы могли бы использовать отсортированную природу и, следовательно, использовать np.searchsorted для этой задачи, например, -

out = np.empty((len(zbin)-1, len(lst)),dtype=int)
for i,l in enumerate(lst):
    left_idx = np.searchsorted(l, zbin[:-1], 'left')
    right_idx = np.searchsorted(l, zbin[1:], 'right')
    out[:,i] = right_idx - left_idx
0 голосов
/ 16 мая 2018

Я думаю, что было бы трудно превзойти производительность, просто повторяя каждый массив и вызывая numpy.histogram.Я полагаю, вы не пробовали этого или упомянули об этом!

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...