如何让Python fill_between与时间序列TEC数据点对齐?
TEC时间序列地震异常检测:滚动置信区间偏移问题
我正在开展一项基于总电子含量(TEC)时间序列数据的项目,目标是通过统计分析识别地震引发的TEC异常。最初参考滑动IQR方法未得到预期结果,转而采用滚动均值+1.67倍标准差的方法。当前遇到的问题是:使用ax.fill_between绘制置信区间时,区间带与TEC数据点偏移了一个窗口步长,即使计算滚动统计量后删除空值也无法解决。
代码实现
df = DAEJ.copy() window = 12 hourly = df.resample(rule="h").median() hourly["ma"] = hourly["TEC"].rolling(window=window).mean() hourly["hour"] = hourly.index.hour hourly["std_err"] = hourly["TEC"].rolling(window=window).std() hourly["ub"] = hourly["ma"] + (1.67* hourly["std_err"]) hourly["lb"] = hourly["ma"] - (1.67* hourly["std_err"]) hourly["sig2"] = hourly["TEC"].rolling(window=window).var() hourly["kur"] = hourly["TEC"].rolling(window=window).kurt() hourly["pctChange"] = hourly.TEC.pct_change(12, fill_method="bfill") hourly = hourly.dropna() dTEC = hourly[(hourly["TEC"] > hourly["ub"])] fig, ax = plt.subplots(figsize=(12,4)) hourly["TEC"].plot(ax=ax, title="TEC Anomaly", label="Station: DAEJ") ax.fill_between(x=hourly.index, y1=hourly["ub"], y2=hourly["lb"], color="red", label="Conf Interval", alpha=.4) ax.legend()
问题现象

问题根源与修复方案
问题原因
Pandas的rolling()方法默认将滚动统计量(均值、标准差)对齐到窗口的右端点:以窗口大小12为例,第12个时间点的均值是前12个时间点(包含当前点)的汇总值,这个统计量本质是对前12个时段的概括,与当前时间点的TEC值在时序对应上会出现偏移,也就是你看到的“区间带偏移一步”。
修复方法
调整rolling()的对齐方式,将统计量对齐到窗口的中心位置,这样置信区间就能和对应时段的TEC数据匹配:
在计算滚动均值和标准差时添加center=True参数:
hourly["ma"] = hourly["TEC"].rolling(window=window, center=True).mean() hourly["std_err"] = hourly["TEC"].rolling(window=window, center=True).std()
修改后,每个窗口的统计量会被放置在窗口的中间位置,置信区间即可与TEC数据点正确对齐。
补充说明
如果业务逻辑要求统计量必须对齐到窗口右端(比如用前12小时的统计量判断当前小时的异常),可保持默认对齐,但需要将置信区间结果向前偏移window//2步,同时对应的异常判断逻辑也要做相应调整。
内容的提问来源于stack exchange,提问作者Imtiaz Nabi
相关产品推荐
相关产品推荐

