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

如何在DataFrame中按日筛选满足前置行条件的第3行并生成sig列

问题

需要为大型DataFrame新增一列值为0或1的sig列,规则如下:

  • 仅针对每日08:30开始的第3行进行判断:若该行data值 > 上一行data值 > 上上行data值,则sig设为1,否则为0;
  • 其余所有行的sig值固定为0;
  • 限制:原始DataFrame的时间戳秒间隔不固定,无法通过时间间隔判断行位置,且每日的总行数不固定。

示例DataFrame

import pandas as pd
import numpy as np

pd.set_option('display.max_rows', 500)
np.random.seed(100)
dates = pd.date_range("2022.01.01", "2022.01.31", freq="s")
dates=dates[:-1]
df = pd.DataFrame({'date':dates,
                   'data':np.random.randint(low=0, high=100, size=len(dates)).tolist()})
df['_date'] = pd.to_datetime(df['date'])
df.set_index('date', inplace=True)   
df = df.loc[(df._date.dt.hour == 8) &  (df._date.dt.minute == 30) &  ((df._date.dt.second >= 0) & (df._date.dt.second <= 10))].head(30)
df.drop(['_date'], axis=1, inplace=True)

示例输出(处理前):

data
date    
2022-01-01 08:30:00 14
2022-01-01 08:30:01 27
2022-01-01 08:30:02 33
2022-01-01 08:30:03 77
2022-01-01 08:30:04 66
2022-01-01 08:30:05 60
2022-01-01 08:30:06 72
2022-01-01 08:30:07 21
2022-01-01 08:30:08 70
2022-01-01 08:30:09 60
2022-01-01 08:30:10 76
2022-01-02 08:30:00 13
2022-01-02 08:30:01 73
2022-01-02 08:30:02 71
2022-01-02 08:30:03 78
2022-01-02 08:30:04 50
2022-01-02 08:30:05 80
2022-01-02 08:30:06 48
2022-01-02 08:30:07 24
2022-01-02 08:30:08 29
2022-01-02 08:30:09 43
2022-01-02 08:30:10 75
2022-01-03 08:30:00 11
2022-01-03 08:30:01 52

期望结果

data  sig
date    
2022-01-01 08:30:00 14   0
2022-01-01 08:30:01 27   0
2022-01-01 08:30:02 33   1
2022-01-01 08:30:03 77   0
2022-01-01 08:30:04 66   0
2022-01-01 08:30:05 60   0
2022-01-01 08:30:06 72   0
2022-01-01 08:30:07 21   0
2022-01-01 08:30:08 70   0
2022-01-01 08:30:09 60   0
2022-01-01 08:30:10 76   0
2022-01-02 08:30:00 13   0
2022-01-02 08:30:01 73   0
2022-01-02 08:30:02 71   0
2022-01-02 08:30:03 78   0
2022-01-02 08:30:04 50   0
2022-01-02 08:30:05 80   0
2022-01-02 08:30:06 48   0
2022-01-02 08:30:07 24   0
2022-01-02 08:30:08 29   0
2022-01-02 08:30:09 43   0
2022-01-02 08:30:10 75   0
2022-01-03 08:30:00 11   0
2022-01-03 08:30:01 32   0
2022-01-03 08:30:02 52   1
2022-01-03 08:30:03 44   0
2022-01-03 08:30:03 75   0
解决方案

通过按日期分组+组内排序+行号标记+条件判断的方式实现,代码如下:

# 核心处理逻辑
# 1. 提取日期部分,用于按自然日分组
df['day'] = df.index.date
# 2. 按日期分组,组内按时间排序(确保顺序正确),并为每行分配组内行号(从0开始计数)
df['row_num'] = df.groupby('day').cumcount()
# 3. 初始化sig列为0
df['sig'] = 0
# 4. 筛选每组的第3行(row_num=2),判断连续三行的data递增关系,满足条件则设为1
mask = (df['row_num'] == 2) & \
       (df['data'] > df.groupby('day')['data'].shift(1)) & \
       (df.groupby('day')['data'].shift(1) > df.groupby('day')['data'].shift(2))
df.loc[mask, 'sig'] = 1
# 可选:删除中间辅助列
df.drop(['day', 'row_num'], axis=1, inplace=True)

# 查看结果
print(df)

关键逻辑说明

  • df.index.date:从时间戳索引中提取纯日期,确保同一自然日的行被分到同一组;
  • groupby('day').cumcount():为每组内的行按时间顺序分配行号,完美适配每日行数不固定的场景;
  • shift(1)/shift(2):在组内获取当前行的前1行、前2行data值,实现连续三行的递增判断;
  • 仅对row_num=2的行应用条件判断,其余行保持sig=0,完全符合需求。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.10 22:30:58