【问题标题】:How to check if one Pandas time-series is present in another long time-series?如何检查一个 Pandas 时间序列是否存在于另一个长时间序列中?
【发布时间】:2020-06-21 07:18:03
【问题描述】:

我有两个很长的时间序列。我必须检查 A 系列中是否存在 B 系列(按给定顺序)。

A 系列:1,2,3,4,5,6,5,4,3。 B 系列:3、4、5。

结果:真,索引是小编找到第一个元素的地方。这里,索引:2(因为 3 出现在 A 系列的索引 2 中)

注意:这两个系列都很大。假设 A 包含 50000 个元素,B 包含 350 个。

【问题讨论】:

    标签: python pandas machine-learning time-series


    【解决方案1】:

    一个非常慢的解决方案是将系列转换为列表并检查第一个列表是否是主列表的子集

    def is_series_a_subseries_in_order(main, sub):
        n = len(sub)
        main=main.tolist()
        sub=sub.tolist()
        return any((main[i:i+n] == sub) for i in range(len(main)-n+1))
    

    将返回 TrueFalse

    【讨论】:

      【解决方案2】:

      一种天真的方法是检查 A 中的 B(1)。在您的示例中 B(1) = A(3),所以现在您必须检查 B(2) = A(4) 并继续直到子字符串的结尾...如果不正确,请从 A(4) 开始并一直持续到结尾。

      搜索子字符串的更好方法是应用 Knuth-Morris-Pratt 算法。我会让你搜索更多关于它的信息!

      【讨论】:

        【解决方案3】:

        不幸的是,pandasrolling 方法不允许用作迭代器,尽管计划在 #11704 中实现。
        因此,我们必须自己实现一个滚动窗口来进行子集检查。

        ser_a = pd.Series(data=[1, 2, 3, 4, 5, 6, 5, 4, 3])
        ser_b = pd.Series(data=[3, 4, 5])
        
        slider_df = pd.concat(
            [ser_a.shift(-i)[:ser_b.size] for i in range(ser_a.size - ser_b.size + 1)], 
            axis=1).astype(ser_a.dtype).T
        sub_series = (ser_b == slider_df).all(axis=1)
        # if you want, you can extract only the indices where a subseries was found:
        sub_series_startindex = sub_series.index[sub_series]
        

        我在这里做什么:

        • [ser_a.shift(-i)[:ser_b.size] for i in range(ser_a.size - ser_b.size + 1)]:通过增加ser_a 的移位创建一个“滚动窗口”,限制为要检查的子系列ser_b 的大小。由于最后的班次将产生NaN,因此这些在range 中被排除在外。
        • pd.concat(..., axis=1):连接移位系列,以便 slider_df 包含列中的所有移位。
        • .astype(ser_a.dtype): 是严格可选的。对于大型系列,这可能会提高性能,对于小型系列,它可能会降低性能。
        • .T:转置 df,使子系列索引按轴 0 对齐。
        • sub_series = (ser_b == slider_df).all(axis=1):查找ser_b 匹配子系列的位置。
        • sub_series.index[sub_series]:提取索引,找到匹配的子系列。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2016-07-09
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多