【发布时间】:2017-09-06 04:42:44
【问题描述】:
假设我有一个 NumPy 整数数组。
arr = np.random.randint(0, 1000, 1000)
我有两个数组lower 和upper,分别代表arr 切片的下限和上限。这些间隔是重叠的并且是可变长度的,但是lowers 和uppers 都保证不会减少。
lowers = np.array([0, 5, 132, 358, 566, 822])
uppers = np.array([45, 93, 189, 533, 800, 923])
我想找到由lowers 和uppers 定义的arr 的每个切片的最小值和最大值,并将它们存储在另一个数组中。
out_arr = np.empty((lowers.size, 2))
最有效的方法是什么?我担心没有矢量化方法,因为我看不到如何在循环中绕过索引..
我目前的方法很简单
for i in range(lowers.size):
arr_v = arr[lowers[i]:uppers[i]]
out_arr[i,0] = np.amin(arr_v)
out_arr[i,1] = np.amax(arr_v)
这让我得到了想要的结果,比如
In [304]: out_arr
Out[304]:
array([[ 26., 908.],
[ 18., 993.],
[ 0., 968.],
[ 3., 999.],
[ 1., 998.],
[ 0., 994.]])
但这对我的实际数据来说太慢了。
【问题讨论】:
-
多少个切片,尤其是与
arr的大小相比?好像长短不一?它们可以重叠吗?关于这种迭代的唯一方法是使用accumulate。cumsum例如在某些情况下有效,例如切片和和均值。 -
@hpaulj 是的,它们的长度可变,重叠,对于大约 10^7 个元素的数组,大约有 10^5 个切片。这些也是我从数据库中读取的所有输入,所以我认为在此之前没有任何空间可以“更好地迈出第一步”。
-
np.minimum.reduceat可能适用。这有点挑剔,因为必须混合上限和下限。同样,最终人们只会将问题减少到具有较小值数组的同类问题。但可能仍然值得。 -
@hpaulj 我不太明白
accumulate如何用于数组的这些切片......它不提供运行最大值吗?在使用切片时,我们如何为切片建立左边界?我现在在玩reduceat。 -
这个函数调用了多少次?如果您经常调用它,那么使用 numba 可能是值得的;只需在您直接的解决方案上调用 @jit 即可将我的后 jit 时间从 2.3 秒缩短到 0.08 秒。
标签: python arrays performance numpy