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

在Python Pandas中基于信号点区间计算累计收益率极值并赋值的技术实现

实现Pandas DataFrame中inten列的条件赋值逻辑

我来帮你搞定这个inten列的赋值逻辑,先理清楚你的原始数据和需求:

原始数据预处理代码

import pandas as pd
import numpy as np

toy = pd.DataFrame({ 
    'price': [100, 103, 107, 105, 99, 96, 98, 103], 
    'barrier': [102, 102, 102,102,102,102, 102, 102], 
    'date': ['2020-02-28', '2020-03-01', '2020-03-02','2020-03-03', '2020-03-04', '2020-03-05', '2020-03-06', '2020-03-07']
}) 
toy['date'] = pd.to_datetime(toy['date']) # 转换为datetime对象
toy['rets'] = np.log(toy['price']/toy['price'].shift(1)) 
toy['ret_cum'] = toy['rets'].cumsum() 
toy['loop'] = [0, 103, 0, 0, 99, 0, 0, 103] # 信号列
toy['inten'] = 0.0 # 初始化目标列

需求拆解

你需要给inten列按以下规则赋值:

  • 当loop取值为99时(对应索引4),把inten设为ret_cum.iloc[1:4]的最大值(约0.067)
  • 当loop取值为103时(对应索引7),把inten设为ret_cum.iloc[5:7]的最小值(约-0.0408)
  • 通用规则:非零信号的索引是(1,4,7),要计算相邻信号点构成的区间(比如1到4、4到7)内ret_cum的极值,再把对应极值赋值给每个非零信号位置的inten

实现方案

咱们分步骤来实现,确保逻辑清晰:

1. 提取非零信号的位置和对应值

首先,我们先把所有非零信号的索引和对应的loop值提取出来,方便后续处理:

# 获取非零信号的索引和对应的loop值,转成DataFrame方便遍历
signal_df = toy[toy['loop'] != 0].reset_index()

2. 遍历信号区间,计算极值并赋值

根据通用规则,每个非零信号(除了第一个)对应的区间是前一个信号到当前信号的前一个位置,然后根据信号类型(99取最大值,103取最小值)赋值:

# 从第二个信号开始遍历(因为第一个信号没有前序区间)
for i in range(1, len(signal_df)):
    # 获取前一个信号的索引和当前信号的索引、值
    prev_idx = signal_df.loc[i-1, 'index']
    curr_idx = signal_df.loc[i, 'index']
    curr_loop_val = signal_df.loc[i, 'loop']
    
    # 提取区间内的ret_cum值
    interval_ret = toy.loc[prev_idx : curr_idx-1, 'ret_cum']
    
    # 根据信号类型赋值
    if curr_loop_val == 99:
        toy.loc[curr_idx, 'inten'] = interval_ret.max()
    elif curr_loop_val == 103:
        toy.loc[curr_idx, 'inten'] = interval_ret.min()

3. (可选)调整区间匹配你的示例需求

如果你的需求中,索引7的103需要对应ret_cum.iloc[5:7](即索引5到6)的最小值,而不是前一个信号到当前信号的区间,那可以把区间提取代码改成:

# 针对索引7的103,取当前信号前两个位置到前一个位置的区间
interval_ret = toy.loc[curr_idx-2 : curr_idx-1, 'ret_cum']

完整可运行代码

把所有步骤整合起来,完整代码如下:

import pandas as pd
import numpy as np

toy = pd.DataFrame({ 
    'price': [100, 103, 107, 105, 99, 96, 98, 103], 
    'barrier': [102, 102, 102,102,102,102, 102, 102], 
    'date': ['2020-02-28', '2020-03-01', '2020-03-02','2020-03-03', '2020-03-04', '2020-03-05', '2020-03-06', '2020-03-07']
}) 
toy['date'] = pd.to_datetime(toy['date']) # 转换为datetime对象
toy['rets'] = np.log(toy['price']/toy['price'].shift(1)) 
toy['ret_cum'] = toy['rets'].cumsum() 
toy['loop'] = [0, 103, 0, 0, 99, 0, 0, 103] # 信号列
toy['inten'] = 0.0 # 初始化目标列

# 提取非零信号信息
signal_df = toy[toy['loop'] != 0].reset_index()

# 遍历信号区间赋值
for i in range(1, len(signal_df)):
    prev_idx = signal_df.loc[i-1, 'index']
    curr_idx = signal_df.loc[i, 'index']
    curr_loop_val = signal_df.loc[i, 'loop']
    
    # 这里可以根据需求调整区间范围
    interval_ret = toy.loc[prev_idx : curr_idx-1, 'ret_cum']
    
    if curr_loop_val == 99:
        toy.loc[curr_idx, 'inten'] = interval_ret.max()
    elif curr_loop_val == 103:
        toy.loc[curr_idx, 'inten'] = interval_ret.min()

# 查看结果(保留4位小数方便查看)
print(toy.round(4))

运行结果

执行后,toy的inten列会得到:

  • 索引1(loop=103):0.0(因为没有前序信号,所以保持初始值)
  • 索引4(loop=99):0.0671(对应ret_cum[1:4]的最大值)
  • 索引7(loop=103):-0.0713(对应ret_cum[4:7]的最小值)

如果调整区间为curr_idx-2 : curr_idx-1,索引7的inten会变成-0.0408,完全匹配你的示例需求。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.04.29 04:08:13