我正在使用时间序列数据集,并使用 scikit-learn 中的 IsolationForest 来识别异常值。 IsolationForest 的输出为我提供了一个值为 1 和 -1 的列,其中 1 表示内值,-1 表示离群值。
我需要按 Isolation_forest 列过滤数据,以提取值从 -1 过渡到 1 的段,然后继续,直到值变回 -1。本质上,我想捕获这些段的第一个实例,其中 Isolation_forest 从 -1 更改为 1,并持续到下一次转换为 -1。
这是我的 DataFrame 的简化示例:
时间 | X | 是 | Z | 隔离_森林 |
---|---|---|---|---|
0 | 12 | 45 | 67 | -1 |
1 | 34 | 23 | 89 | -1 |
2 | 56 | 78 | 12 | 1 |
3 | 23 | 45 | 67 | 1 |
4 | 89 | 12 | 34 | 1 |
5 | 45 | 67 | 89 | 1 |
6 | 78 | 23 | 12 | -1 |
7 | 12 | 89 | 45 | -1 |
8 | 34 | 67 | 78 | -1 |
9 | 56 | 12 | 23 | 1 |
10 | 67 | 34 | 56 | 1 |
在此示例中,我想提取从第一次在时间 2 处转换到 1 开始的段,直到下一次在时间 6 处转换到 -1 为止。结果应如下所示:
时间 | X | 是 | Z | 隔离_森林 |
---|---|---|---|---|
2 | 56 | 78 | 12 | 1 |
3 | 23 | 45 | 67 | 1 |
4 | 89 | 12 | 34 | 1 |
5 | 45 | 67 | 89 | 1 |
我尝试使用
过滤DataFramedf_filtered = df.loc[df['Isolation_forest'] == 1]
但是,此方法包括 Isolation_forest 为 1 的所有行,而不仅仅是从 -1 到 1 再回到 -1 的转换之间的段。
如何使用 pandas 以编程方式从 DataFrame 中过滤这些段?
您可以根据 -1 或 1 的连续运行创建组编号。(此代码是从 jezrael 复制的。)
groups = df['Isolation_forest'].ne(df['Isolation_forest'].shift()).cumsum()
然后您只需进行过滤,就像您已经做的那样。
for k, group in df.loc[df['Isolation_forest'] == 1].groupby(groups):
print(k)
print(group)
print()
输出:
2
Time X Y Z Isolation_forest
2 2 56 78 12 1
3 3 23 45 67 1
4 4 89 12 34 1
5 5 45 67 89 1
4
Time X Y Z Isolation_forest
9 9 56 12 23 1
10 10 67 34 56 1