python - NumPy:按索引分割的一维数组求和

标签 python numpy split sum vectorization

考虑一个一维 NumPy 输入数组和一个排序索引数组。目标是获得输入数组 a 的总和,但按索引数组中定义的索引进行分割。

下面有两种方法,但它们都需要缓慢的 Python for 循环。是否有不需要 Python for 循环的纯 NumPy 版本?

示例:

a = np.arange(20) # Input array
idxs = np.array([7, 15, 16]) # Index array

# Goal: Split a at index 7, 15 and 16 and
# compute sum for each partition

# Solution 1:
idxs_ext = np.concatenate(([0], idxs, [a.size]))
results = np.empty(idxs.size + 1)
for i in range(results.size):
    results[i] = a[idxs_ext[i]:idxs_ext[i+1]].sum()

# Solution 2:
result = np.array(
    [a_.sum() for a_ in np.split(a, idxs)]
)

# Result: array([21., 84., 15., 70.])

最佳答案

首先,您可以根据 idxs 数组通过 np.split 拆分 a 数组,然后将函数应用到该数组上,如下所示:

np.stack(np.vectorize(np.sum)(np.array(np.split(a, idxs), dtype=object)))

另一个答案是使用 np.add.reduceat 正如 @hpaulj 在评论中提到的那样,速度更快:

np.add.reduceat(a, np.insert(idxs, 0, 0), axis=0)

更新:
对于具有 7 个切片的数据范围 1000,使用 np.concatenate 代替 insert 将运行时间减少了 5 倍; 这是我研究过的最快的方法:

np.add.reduceat(a, np.concatenate(([0], idxs)), axis=0)

关于python - NumPy:按索引分割的一维数组求和,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/70322757/

相关文章:

javascript - 通过新行(包括空行)将textarea中的文本拆分为javascript数组

python - 如何配置 Visual Studio Code 以在 virtualenv 中调试 Django 应用程序?

python - @api.depends 依赖于非存储字段不起作用

Linux:使用Python捕获发送到ULOG的数据包? (带宽监控项目)

python - 将字典中的值打印到新的 csv 文件中

python - 使用 numpy ufuncs 就地修改 Pandas 数据框

Javascript 电话验证功能在 IE8 中不起作用

python - 如何在 Python 3 中测试所有可迭代对象是否为真

python - 在for循环中对压缩列表进行排序

java - 正则表达式根据分割索引处的长度和相邻字符分割字符串