我有以下工作代码,在starts和ends指定的位置将1设置为“ends”。
import pandas as pd
import numpy as np
df = pd.DataFrame({"a": np.arange(10)})
starts = [1, 5, 8]
ends = [1, 6, 10]
value = 1
df["new_col"] = 0
for s, e in zip(starts, ends):
df.loc[s:e, "new_col"] = value
print(df)a new\_col 0 0 0 1 1 1 2 2 0 3 3 0 4 4 0 5 5 1 6 6 1 7 7 0 8 8 1 9 9 1
我希望这些间隔来自另一个dataframe pointer_df。
如何矢量化?
pointer_df = pd.DataFrame({"starts": starts, "ends": ends})企图:
df.loc[pointer_df["starts"]:pointer_df["ends"], "new_col"] = 2
print(df)显然不起作用
raise AssertionError("Start slice bound is non-scalar") AssertionError: Start slice bound is non-scalar
编辑:
似乎所有的答案都是用某种琵琶来循环的。
问题是如何将上面的操作矢量化?
如果没有for循环/列表理解,这不是可行的吗?
发布于 2020-12-01 17:43:00
你可以这样做:
pointer_df = pd.DataFrame({"starts": starts, "ends": ends})
rang = np.arange(len(df))
indices = [i for s, e in pointer_df.to_numpy() for i in rang[slice(s, e + 1, None)]]
df.loc[indices, 'new_col'] = value
print(df)输出
a new_col
0 0 0
1 1 1
2 2 0
3 3 0
4 4 0
5 5 1
6 6 1
7 7 0
8 8 1
9 9 1如果希望方法不使用任何for循环或列表理解,而只依赖于numpy,则可以:
def indices(start, end, ma=10):
limits = end + 1
lens = np.where(limits < ma, limits, end) - start
np.cumsum(lens, out=lens)
i = np.ones(lens[-1], dtype=int)
i[0] = start[0]
i[lens[:-1]] += start[1:]
i[lens[:-1]] -= limits[:-1]
np.cumsum(i, out=i)
return i
pointer_df = pd.DataFrame({"starts": starts, "ends": ends})
df.loc[indices(pointer_df.starts.values, pointer_df.ends.values, ma=len(df)), "new_col"] = value
print(df)我从这个answer中的用例中调整了该方法。
发布于 2020-12-01 17:43:13
for i,j in zip(pointer_df["starts"],pointer_df["ends"]):
print (i,j)在字典上使用相同的方法
https://stackoverflow.com/questions/65095415
复制相似问题