3. 负荷预测基础:时间序列分析、ARIMA模型原理、基于Python的负荷预测实现

各位同学,咱们今天聊点实在的——负荷预测。做电力市场交易,说白了就是跟不确定性打交道。而负荷预测,就是咱们手里最基础的那把尺子。

我个人习惯把负荷预测比作“看天吃饭”。天气变化有规律,但也有突发情况。负荷也一样,有趋势、有周期、有随机波动。咱们要做的,就是把这些规律找出来。

3.1 时间序列分析:先看懂数据再说

时间序列,说白了就是按时间顺序排好的数据。电力负荷数据,天然就是时间序列——每15分钟一个点,一天96个点,一年35040个点。

我刚开始做负荷预测时,犯过一个低级错误:拿到数据直接建模,结果一塌糊涂。后来才明白,数据预处理比建模本身更重要

3.1.1 时间序列的三个核心成分

任何一个时间序列,都可以拆成三部分:

  • 趋势成分:长期上升或下降。比如某地区经济发展,用电量逐年增加。
  • 季节成分:固定周期的波动。比如每天早晚高峰、每周工作日与周末差异、每年冬夏用电高峰。
  • 残差成分:随机波动。比如某天突然降温,空调负荷猛增。

为什么要拆?因为不同的成分,需要用不同的方法去处理。

核心观点:预测不是猜未来,而是把历史规律外推。但外推的前提是——规律要稳定。

3.1.2 平稳性:建模的前提条件

这里有个关键概念——平稳性。什么叫平稳?简单说就是:数据的统计性质不随时间变化。

举个例子:某地区负荷均值是1000MW,方差是200MW²。如果这个均值和方差在10年前、5年前、现在都差不多,那这个序列就是平稳的。

但现实中的负荷数据,几乎都不平稳。为什么?因为经济发展、人口增长、产业结构调整,都会让均值发生变化。

注意:用非平稳数据直接建模,会出现“伪回归”问题——模型看起来拟合得很好,但预测一塌糊涂。我曾经吃过这个亏,模型R²高达0.95,结果预测误差超过30%。

3.2 ARIMA模型原理:从自回归到移动平均

ARIMA,全称是自回归积分滑动平均模型。名字挺唬人,但拆开看就明白了。

3.2.1 三个字母的含义

字母 全称 含义
AR 自回归 用过去的值预测现在的值。比如今天的负荷跟昨天、前天的负荷有关。
I 积分 差分操作,把非平稳序列变成平稳序列。
MA 移动平均 用过去的预测误差来修正当前的预测。

ARIMA模型有三个参数:p(自回归阶数)、d(差分阶数)、q(移动平均阶数)。写成ARIMA(p,d,q)。

3.2.2 差分:化非平稳为平稳

差分操作,说白了就是“相邻相减”。

一阶差分:Δy_t = y_t - y_{t-1}
二阶差分:Δ²y_t = Δy_t - Δy_{t-1}

我遇到过一种情况:某地区负荷数据有明显的线性增长趋势,一阶差分后序列就平稳了。但有些数据需要二阶差分才行。记住一个原则:能用一阶差分就别用二阶,因为差分次数越多,信息损失越大。

3.2.3 模型定阶:怎么选p和q

选p和q,常用的方法有两种:

  • 自相关函数(ACF):看当前值与滞后值之间的相关性。如果ACF在滞后q后截尾,那q就是MA的阶数。
  • 偏自相关函数(PACF):剔除中间变量影响后的相关性。如果PACF在滞后p后截尾,那p就是AR的阶数。

但说实话,实际项目中我很少完全依赖ACF和PACF。因为数据往往没那么“干净”。我更习惯用信息准则(AIC/BIC)自动搜索最优参数。

我的经验:对于电力负荷数据,p和q通常不会超过7。因为负荷的周期性一般是7天(周周期)或24小时(日周期)。超过这个范围,模型容易过拟合。

3.3 基于Python的负荷预测实现

理论说完了,咱们动手。我用Python的statsmodels库来实现ARIMA模型。

3.3.1 数据准备

import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from statsmodels.tsa.stattools import adfuller
from statsmodels.graphics.tsaplots import plot_acf, plot_pacf
from statsmodels.tsa.arima.model import ARIMA
from sklearn.metrics import mean_absolute_error, mean_squared_error

# 加载数据(假设是某地区2019-2020年的日负荷数据)
df = pd.read_csv('load_data.csv', parse_dates=['date'], index_col='date')
print(df.head())
print(df.info())

3.3.2 平稳性检验

用ADF检验来判断序列是否平稳。

def test_stationarity(timeseries):
    # 滚动统计
    rolmean = timeseries.rolling(window=12).mean()
    rolstd = timeseries.rolling(window=12).std()
    
    # ADF检验
    result = adfuller(timeseries.dropna())
    print('ADF Statistic: %f' % result[0])
    print('p-value: %f' % result[1])
    
    if result[1] < 0.05:
        print('序列平稳')
    else:
        print('序列非平稳,需要进行差分')

test_stationarity(df['load'])

如果p值大于0.05,说明序列非平稳。这时候就需要差分。

3.3.3 模型训练与预测

# 一阶差分
df['load_diff'] = df['load'].diff().dropna()

# 再次检验平稳性
test_stationarity(df['load_diff'].dropna())

# 确定p和q(这里用AIC自动搜索)
from statsmodels.tsa.arima.model import ARIMA
import itertools

p = range(0, 8)
d = [1]  # 一阶差分
q = range(0, 8)

best_aic = float('inf')
best_params = None

for p_val, d_val, q_val in itertools.product(p, d, q):
    try:
        model = ARIMA(df['load'], order=(p_val, d_val, q_val))
        results = model.fit()
        if results.aic < best_aic:
            best_aic = results.aic
            best_params = (p_val, d_val, q_val)
    except:
        continue

print(f'最优参数: ARIMA{best_params}, AIC={best_aic:.2f}')

# 用最优参数训练最终模型
final_model = ARIMA(df['load'], order=best_params)
final_results = final_model.fit()

# 预测未来7天
forecast = final_results.forecast(steps=7)
print('未来7天负荷预测值:')
print(forecast)

3.3.4 模型评估

# 划分训练集和测试集
train = df['load'][:-30]
test = df['load'][-30:]

# 在训练集上重新训练
model = ARIMA(train, order=best_params)
results = model.fit()

# 预测测试集
predictions = results.forecast(steps=len(test))

# 计算误差
mae = mean_absolute_error(test, predictions)
rmse = np.sqrt(mean_squared_error(test, predictions))
mape = np.mean(np.abs((test - predictions) / test)) * 100

print(f'MAE: {mae:.2f} MW')
print(f'RMSE: {rmse:.2f} MW')
print(f'MAPE: {mape:.2f}%')

注意:MAPE(平均绝对百分比误差)是电力行业最常用的指标。一般要求MAPE < 3%。如果超过5%,说明模型需要改进。

3.4 知识体系总览

下面这张图,把本章的核心逻辑串起来了。我建议你保存下来,做项目时对照着看。

负荷预测知识体系 原始负荷数据 数据预处理(缺失值、异常值、平稳化) ARIMA模型(p,d,q参数确定) ACF/PACF定阶 AIC/BIC自动搜索 残差检验 负荷预测结果(含误差评估)

3.5 避坑指南

做负荷预测这些年,我踩过不少坑。挑几个典型的说说:

  • 坑一:忽略节假日效应。春节、国庆等长假,负荷模式完全不一样。我建议单独建一个节假日模型,或者用虚拟变量处理。
  • 坑二:过度差分。有些同学看到序列不平稳,就反复差分。结果序列是平稳了,但原始信息也丢得差不多了。记住:差分次数d一般不超过2
  • 坑三:忽视残差检验。模型训练完,一定要检查残差是不是白噪声。如果残差还有自相关,说明模型没捕捉到所有信息,需要调整参数。

我的建议:刚开始做负荷预测,别追求复杂的模型。先把ARIMA用熟,把数据预处理做好。很多时候,一个调参得当的ARIMA模型,效果比那些花里胡哨的深度学习模型还好。

好了,这一章的内容就到这儿。负荷预测是电力市场交易的基础,把这块打扎实了,后面做价格预测、交易策略才能得心应手。


公众号:蓝海资料掘金营,微信deep3321