我有排序(一维)不等长度的数组(比如M0
,M1
和{{1} })。我想找到每个数组中有多少元素在特定数字范围内(其中数字范围由来自另一个有序数组的相邻元素指定,例如{{1 }})。我想知道实现这一目标的最快方式是什么。
在这里,我给出了我想要做的任务的一个小例子(以及我目前为实现所需功能而遵循的方法):
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]
。)例如,请考虑bin [5.5, 6.0]
。数组[6.0, 6.5]
在该bin([5.0, 5.5]
和M0
)中有 2 个元素,5.1
有 1 元素( 5.4
)和M1
在该bin中有 0 个元素。这给出了5.2
的第一行,即M2
。可以以类似的方式获得zarr
的其他行。
在我的实际任务中,我将处理[2,1,0]
长度远大于我在此示例中给出的长度,以及更大和更多的数组,如zarr
,zbin
,M0
M1
。所有...
和数组Mn
将始终排序。我想知道我设计的功能(M
)和我所遵循的方法是否是实现所需功能的最佳方式和最快方式。我真的很感激任何帮助。
答案 0 :(得分:2)
我们可以利用排序的性质,因此使用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
答案 1 :(得分:1)
我猜想要简单地循环遍历每个数组并调用numpy.histogram会很难。我猜你没试过这个,或者你已经提到了它!
你当然可以利用排序的性质来提出更快的解决方案,但我首先要比较它的时间。