You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何提取pandas DataFrame指定起止值的单调递增连续切片

pandas提取指定起止值的单调递增连续切片

匹配规则

  • 切片严格以设定的起始值开头、终止值结尾
  • 切片内speed列数值单调递增
  • 忽略切片范围外的所有其他数据

实现逻辑

使用diff()、cummax()类方案结果异常的核心原因是未提前对连续递增片段做分段切割,跨非递增区间的判断会导致逻辑混乱,正确处理步骤如下:

  • 第一步:识别所有连续单调递增的数据段,只要当前行speed值小于前一行,就标记为递增中断、新段开启,给每个独立的递增段分配唯一ID
  • 第二步:定位所有值等于起始值的位置作为候选起点
  • 第三步:逐个检查候选起点所属的递增段,若段内存在目标终止值,则截取从起点位置到终止值位置的连续行即为结果,分段逻辑已经天然保证片段内数据单调递增,无需额外做单调性校验

代码实现

import pandas as pd 
import numpy as np

# 示例测试数据
speed = [0,1,2,3,4,5,6,7,8,9,0,11,12,13,14,15,14,13,11,12,15,12,14,16,11,10,9,5,12,20,21,22,25,27,32,34,35,30,20]
df = pd.DataFrame(speed, columns=['speed']) 

def get_target_slice(df, start_val, end_val, target_col='speed'):
    # 标记递增断点,生成连续递增段ID
    is_decrease = df[target_col].diff() < 0
    seg_mark = is_decrease.cumsum()
    
    # 遍历所有候选起点
    for start_idx in df.index[df[target_col] == start_val]:
        current_seg_id = seg_mark.loc[start_idx]
        # 提取起点之后同属一个递增段的所有数据
        current_seg_data = df.loc[start_idx:][seg_mark.loc[start_idx:] == current_seg_id, target_col]
        # 检查当前段是否包含终止值
        if end_val in current_seg_data.values:
            end_idx = current_seg_data[current_seg_data == end_val].index[0]
            return df.loc[start_idx:end_idx, [target_col]].reset_index(drop=True)
    # 无符合条件片段时返回空表
    return pd.DataFrame(columns=[target_col])

# 测试:起始值20、终止值35
result = get_target_slice(df, 20, 35)
print(result)

输出结果

speed
0     20
1     21
2     22
3     25
4     27
5     32
6     34
7     35

和预期结果完全匹配。

性能说明

全表仅做一次向量化差分、累计求和运算,后续仅遍历候选起点位置,无全表逐行循环,百万行级大型DataFrame也可以快速处理。


内容的提问来源于stack exchange,提问作者SomeOne

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.28 12:16:02