在另一个Q + A(我可以在pandas中执行动态cumsum?)我对使用prange这个代码的正确性做了评论(这个答案):
from numba import njit, prange
@njit
def dynamic_cumsum(seq, index, max_value):
cumsum = []
running = 0
for i in prange(len(seq)):
if running > max_value:
cumsum.append([index[i], running])
running = 0
running += seq[i]
cumsum.append([index[-1], running])
return cumsum
Run Code Online (Sandbox Code Playgroud)
评论是:
我不建议并行化一个不纯的循环.在这种情况下,
running变量使其不纯.有4种可能的结果:(1)numba决定它不能并行处理它只是处理循环cumsum而不是prange(2)它可以将变量提升到循环之外并在余数上使用并行化(3)numba错误地插入并行执行和结果之间的同步可能是虚假的(4)numba在运行时插入必要的同步,这可能会比通过并行化首先获得更多的开销
而后来的补充:
当然,
running和cumsum变量都使循环"不纯",而不仅仅是前面评论中所述的运行变量
然后我被问到:
这可能听起来像一个愚蠢的问题,但我怎么能弄清楚它做了哪4件事并改进了呢?我真的想用numba变得更好!
鉴于它可能对未来的读者有用,我决定在这里创建一个自我回答的Q + A. 掠夺者:我无法真正回答4个结果中的哪一个产生的问题(或者如果numba产生完全不同的结果),所以我非常鼓励其他答案.
数据
让我们采用以下二维数组:
starts = [0, 4, 10, 13, 23, 27]
ends = [4, 10, 13, 23, 27, 32]
lengths = [4, 6, 3, 10, 4, 5]
arr = np.array([starts, ends, lengths]).T
Run Code Online (Sandbox Code Playgroud)
因此看起来像:
[[ 0 4 4]
[ 4 10 6]
[10 13 3]
[13 23 10]
[23 27 4]
[27 32 5]]
Run Code Online (Sandbox Code Playgroud)
目标
现在我想“循环”通过lengthsand 一旦累积和达到10我想输出startsandends然后重新启动累积计数。
工作代码
tot_size = 0
start = 0
for i, numb in enumerate(arr[:,-1]):
# update sum
tot_size += …Run Code Online (Sandbox Code Playgroud) 我有一个表示分数时间序列的 Pandas DataFrame。我想使用该分数根据以下标准计算 CookiePoints 列:
请参阅下面的示例:
Score CookiePoints
14 0
13 0
14 1
17 2
17 0
19 1
20 2
22 3
23 1
17 0
19 1
20 2
22 3
21 0
Run Code Online (Sandbox Code Playgroud)
请注意,这是一个最小的、可重现的示例。解决方案必须使用 Pandas DataFrame,并且理想情况下仅使用矢量化操作。