4. 机器学习预测方法:特征工程构建与模型调参
好,咱们进入正题。这一章我打算聊聊机器学习在负荷预测里的实战套路。说白了,就是怎么把一堆原始数据变成模型能看懂的特征,再让随机森林和XGBoost这两个老伙计帮我们把预测做准。
我个人习惯把特征工程放在模型前面讲。为什么?因为模型再牛,喂进去的是垃圾,吐出来的还是垃圾。我在项目里吃过这个亏,后来就学乖了。
4.1 特征工程:从原始数据到有效特征
特征工程,说白了就是给模型找“线索”。你想想看,负荷变化不是凭空来的,它跟时间、天气、历史负荷都有关系。我们要做的,就是把这三类线索挖出来。
4.1.1 时间特征
时间特征是最基础的。我一般会从时间戳里拆出下面这些:
- 小时:0-23,反映日内用电规律。比如晚上8点是高峰,凌晨3点是低谷。
- 星期几:0-6,区分工作日和周末。周一和周六的负荷曲线差别很大。
- 月份:1-12,捕捉季节性变化。夏天开空调,冬天取暖,负荷完全两码事。
- 是否节假日:0或1。节假日负荷通常比工作日低20%-30%。
- 一年中的第几天:1-365,用来捕捉长期趋势。
4.1.2 气象特征
气象特征对负荷预测影响很大,尤其是温度。我在项目中遇到过,夏天温度每升高1℃,空调负荷可能增加5%-8%。
常用的气象特征包括:
- 温度:当前温度、最高温、最低温
- 湿度:影响体感温度,间接影响空调使用
- 风速:大风天可能影响供暖或制冷需求
- 降雨/降雪:0或1,恶劣天气会改变用电行为
- 体感温度:综合温度和湿度的计算值,比单纯温度更准
4.1.3 历史负荷特征
历史负荷是预测当前负荷最重要的依据。我常用的做法是:
- 前1小时负荷:短期惯性
- 前24小时同时刻负荷:日周期性
- 前168小时同时刻负荷:周周期性(7天前同一时刻)
- 滑动平均:过去3小时、6小时的平均负荷,平滑噪声
- 滑动标准差:反映负荷波动程度
嗯,这里要注意:历史负荷特征不能引入未来信息。比如你要预测t时刻的负荷,只能用t-1、t-24这些过去的数据,不能用t+1的。
4.2 随机森林回归实战
随机森林是个好用的模型。它由多棵决策树组成,每棵树都在数据子集和特征子集上训练,最后取平均。说白了就是“三个臭皮匠,顶个诸葛亮”。
下面是我常用的代码模板:
from sklearn.ensemble import RandomForestRegressor
from sklearn.model_selection import GridSearchCV
# 初始化模型
rf = RandomForestRegressor(random_state=42)
# 参数网格
param_grid = {
'n_estimators': [100, 200, 300],
'max_depth': [10, 15, 20, None],
'min_samples_split': [2, 5, 10],
'min_samples_leaf': [1, 2, 4]
}
# 网格搜索
grid_search = GridSearchCV(
rf, param_grid,
cv=5,
scoring='neg_mean_squared_error',
n_jobs=-1
)
grid_search.fit(X_train, y_train)
# 最佳参数
print("最佳参数:", grid_search.best_params_)
4.3 XGBoost模型调参与评估
XGBoost是梯度提升树的升级版。它比随机森林更准,但调参也更讲究。我在项目中试过,同样的数据,XGBoost比随机森林的RMSE低了8%左右。
XGBoost的核心参数:
| 参数 | 作用 | 推荐范围 |
|---|---|---|
| n_estimators | 树的数量 | 100-1000 |
| learning_rate | 学习率,控制每棵树的贡献 | 0.01-0.3 |
| max_depth | 树的最大深度 | 3-10 |
| subsample | 每棵树使用的样本比例 | 0.6-1.0 |
| colsample_bytree | 每棵树使用的特征比例 | 0.6-1.0 |
| reg_alpha | L1正则化 | 0-10 |
| reg_lambda | L2正则化 | 0-10 |
调参顺序我建议这样:
- 先定学习率和树的数量。学习率0.1,树的数量用早停法确定。
- 调max_depth和min_child_weight。深度从3开始试。
- 调subsample和colsample_bytree,防止过拟合。
- 最后调正则化参数reg_alpha和reg_lambda。
import xgboost as xgb
# 定义模型
xgb_model = xgb.XGBRegressor(
n_estimators=500,
learning_rate=0.1,
max_depth=5,
subsample=0.8,
colsample_bytree=0.8,
random_state=42
)
# 训练
xgb_model.fit(
X_train, y_train,
eval_set=[(X_val, y_val)],
early_stopping_rounds=50,
verbose=False
)
# 预测
y_pred = xgb_model.predict(X_test)
4.4 模型评估指标
评估模型好不好,不能光看一个指标。我一般用下面几个:
| 指标 | 公式 | 说明 |
|---|---|---|
| MAE | 平均绝对误差 | 直观反映预测偏差大小 |
| RMSE | 均方根误差 | 对大误差惩罚更大 |
| MAPE | 平均绝对百分比误差 | 反映相对误差,适合对比 |
| R² | 决定系数 | 模型解释了多少方差 |
我个人习惯重点看RMSE和MAPE。RMSE能反映大偏差的情况——比如有没有出现某个时刻预测完全跑偏。MAPE则能看出整体精度,一般MAPE在5%以内就算不错了。
4.5 本章知识体系
下面这张图把本章的核心逻辑串起来了。从原始数据出发,经过特征工程,再到模型训练和评估,每一步都有坑也有技巧。
这张图里,我特别想强调左侧那条虚线——数据更新后要重新训练模型。我在项目里见过有人模型训完就不管了,结果半年后预测精度从5%掉到15%。负荷模式是会变的,模型也得跟着更新。
好了,这一章的内容就到这儿。特征工程、随机森林、XGBoost调参,这三块你吃透了,负荷预测的基本功就算打牢了。
公众号:蓝海资料掘金营,微信deep3321