我有一个包含浮点值的数据框
my_df = pd.DataFrame([1,2,1,4,3,2,5,4,7])
我试图为每个数字查找何时(需要向前移动多少索引),直到找到比当前数字大的下一个数字为止,如果没有更大的数字,则将其标记为某个值(例如999999)。
因此,对于以上示例,正确答案应为
result = [1,2,1,3,2,1,2,1,999999]
目前,我已经通过非常慢的双循环来解决了这个问题itertuples
(意思是O(n ^ 2))
有更聪明的方法吗?
这是一个基于numpy的利用广播的方式:
a = my_df.squeeze().to_numpy() # my_df.squeeze().values for versions 0.24.0.<
diff_mat = a - a[:,None]
result = (np.triu(diff_mat)>0).argmax(1) - np.arange(diff_mat.shape[1])
result[result <= 0] = 99999
print(result)
array([ 1, 2, 1, 3, 2, 1, 2, 1, 99999],
dtype=int64)
diff_mat
距离矩阵在哪里,我们正在寻找从主对角线开始的值,这些值大于0
:
array([[ 0, 1, 0, 3, 2, 1, 4, 3, 6],
[-1, 0, -1, 2, 1, 0, 3, 2, 5],
[ 0, 1, 0, 3, 2, 1, 4, 3, 6],
[-3, -2, -3, 0, -1, -2, 1, 0, 3],
[-2, -1, -2, 1, 0, -1, 2, 1, 4],
[-1, 0, -1, 2, 1, 0, 3, 2, 5],
[-4, -3, -4, -1, -2, -3, 0, -1, 2],
[-3, -2, -3, 0, -1, -2, 1, 0, 3],
[-6, -5, -6, -3, -4, -5, -2, -3, 0]], dtype=int64)
我们np.triu
为此:
np.triu(diff_mat)
array([[ 0, 1, 0, 3, 2, 1, 4, 3, 6],
[ 0, 0, -1, 2, 1, 0, 3, 2, 5],
[ 0, 0, 0, 3, 2, 1, 4, 3, 6],
[ 0, 0, 0, 0, -1, -2, 1, 0, 3],
[ 0, 0, 0, 0, 0, -1, 2, 1, 4],
[ 0, 0, 0, 0, 0, 0, 3, 2, 5],
[ 0, 0, 0, 0, 0, 0, 0, -1, 2],
[ 0, 0, 0, 0, 0, 0, 0, 0, 3],
[ 0, 0, 0, 0, 0, 0, 0, 0, 0]], dtype=int64)
通过检查哪个大于0
,并采用argmax
布尔值,ndarray
我们将发现第一个值大于0
每行:
(np.triu(diff_mat)>0).argmax(1)
array([1, 3, 3, 6, 6, 6, 8, 8, 0], dtype=int64)
我们只需要从主对角线到起点减去相应的偏移量
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句