深度学习篇---概率预测
概率预测通过概率分布描述未来结果,相比传统单点预测更能量化不确定性。其核心价值体现在:1)显式表达预测可靠性,区分不同置信度;2)支持风险评估和应急决策;3)提供完整信息供多方案规划。常用实现方法包括分位数回归、贝叶斯方法和深度学习概率预测,通过输出置信区间和概率分布取代单一数值。实际应用中,概率预测可优化库存管理(动态调整安全库存)和风险管理(计算在险价值),推动决策从盲目相信数字转向基于完整信
一、本质是什么?
核心比喻:从"猜数字"到"划范围"
传统单点预测(猜数字):
"明天中午的气温将会是 25.3°C。"
概率预测(划范围):
"明天中午的气温:
有50%的可能性在 24.5°C - 26.1°C 之间
有90%的可能性在 23.8°C - 26.8°C 之间
最可能出现在 25.3°C 左右"
技术本质
概率预测的本质是:用概率分布来描述未来可能的结果,而不仅仅是给出一个确定的数值。它量化了预测的不确定性。
关键概念:
-
置信区间:一个数值范围,表示真实值落在这个范围内的概率
-
概率分布:描述所有可能结果及其发生概率的函数
-
分位数预测:预测某个概率阈值对应的数值
数学表达
传统预测:y_pred = f(x)
概率预测:P(Y|X) = f(x)
-
输出是一个概率分布,而不是单个值
-
比如:
Y ~ N(μ=25.3, σ=0.8),表示服从均值为25.3,标准差为0.8的正态分布
二、为什么需要概率预测?
单点预测的局限性
1. 过度自信问题
# 传统预测的"幻觉"
predicted_temperature = 25.3 # 看起来非常精确
# 但实际上真实温度可能是24.8°C或25.8°C,模型没有告诉我们这种不确定性
2. 无法评估风险
-
决策者不知道预测的可靠程度
-
无法进行风险评估和应急预案制定
3. 信息损失
-
忽略了数据中固有的不确定性
-
无法区分"很有把握"和"只是猜测"
概率预测的核心价值
✅ 量化不确定性
-
知道预测的可靠程度
-
区分高置信度和低置信度的预测
✅ 支持更好的决策
# 医疗诊断例子
单点预测:"这个肿瘤有80%可能是良性的"
概率预测:"这个肿瘤有80%可能是良性的,但这个估计的95%置信区间是[65%, 90%]"
# 决策意义:如果置信区间很宽,医生可能会建议进一步检查
✅ 风险管理
-
可以计算"最坏情况"和"最好情况"
-
为极端事件做好准备
✅ 模型评估
-
可以评估预测区间是否校准正确
-
比如:90%的置信区间是否真的包含了90%的真实值
三、怎样做?(具体实现方法)
方法1:分位数回归
这是最常用且直观的方法。
基本思想
预测分布的不同分位数,而不是平均值。
import numpy as np
import matplotlib.pyplot as plt
from sklearn.ensemble import GradientBoostingRegressor
# 生成示例数据
np.random.seed(42)
X = np.linspace(0, 10, 100)
y = 2 * X + np.sin(X) + np.random.normal(0, 0.5, 100)
# 定义要预测的分位数
quantiles = [0.05, 0.25, 0.5, 0.75, 0.95]
plt.figure(figsize=(12, 8))
# 对每个分位数训练一个模型
for i, q in enumerate(quantiles):
# 使用分位数损失训练模型
model = GradientBoostingRegressor(loss='quantile', alpha=q,
n_estimators=100, max_depth=3)
model.fit(X.reshape(-1, 1), y)
# 预测
X_test = np.linspace(0, 10, 200)
y_pred = model.predict(X_test.reshape(-1, 1))
# 绘制
label = f'{int(q*100)}% 分位数'
plt.plot(X_test, y_pred, label=label, linewidth=2)
# 绘制原始数据
plt.scatter(X, y, alpha=0.6, color='black', label='真实数据')
plt.xlabel('X')
plt.ylabel('y')
plt.title('分位数回归 - 概率预测')
plt.legend()
plt.grid(True, alpha=0.3)
plt.show()
方法2:贝叶斯方法
概念理解
不是学习固定的权重,而是学习权重的概率分布。
import pymc3 as pm
import arviz as az
# 贝叶斯线性回归示例
def bayesian_probabilistic_forecasting(X, y):
with pm.Model() as model:
# 先验分布 - 我们对参数的初始信念
alpha = pm.Normal('alpha', mu=0, sigma=10) # 截距
beta = pm.Normal('beta', mu=0, sigma=10) # 斜率
sigma = pm.HalfNormal('sigma', sigma=1) # 噪声标准差(必须为正)
# 线性关系
mu = alpha + beta * X
# 似然函数 - 观测数据如何影响我们的信念
likelihood = pm.Normal('y', mu=mu, sigma=sigma, observed=y)
# 采样 - 从后验分布中抽取样本
trace = pm.sample(1000, tune=1000, return_inferencedata=False)
return trace, model
# 使用示例
# trace, model = bayesian_probabilistic_forecasting(X, y)
方法3:深度学习概率预测
使用TensorFlow Probability
import tensorflow as tf
import tensorflow_probability as tfp
tfd = tfp.distributions
def create_probabilistic_cnn(input_shape):
"""创建概率预测的CNN模型"""
model = tf.keras.Sequential([
# 特征提取层
tf.keras.layers.Conv1D(32, 3, activation='relu', input_shape=input_shape),
tf.keras.layers.MaxPooling1D(2),
tf.keras.layers.Conv1D(64, 3, activation='relu'),
tf.keras.layers.GlobalAveragePooling1D(),
# 概率输出层 - 预测正态分布的参数
tf.keras.layers.Dense(2), # 输出两个参数:均值和标准差
# 概率分布层
tfp.layers.DistributionLambda(
lambda t: tfd.Normal(loc=t[..., :1],
scale=1e-3 + tf.math.softplus(t[..., 1:]))),
])
return model
# 自定义负对数似然损失
def negative_loglikelihood(y_true, y_pred):
return -y_pred.log_prob(y_true)
# 创建和编译模型
# model = create_probabilistic_cnn((10, 1))
# model.compile(optimizer='adam', loss=negative_loglikelihood)
方法4:完整的时间序列概率预测示例
import pandas as pd
from sklearn.preprocessing import StandardScaler
class ProbabilisticTimeSeriesForecaster:
def __init__(self):
self.scaler = StandardScaler()
self.models = {} # 存储不同分位数的模型
def prepare_features(self, series, lookback=10):
"""准备时间序列特征"""
X, y = [], []
for i in range(lookback, len(series)):
X.append(series[i-lookback:i])
y.append(series[i])
return np.array(X), np.array(y)
def train_quantile_models(self, series, quantiles=[0.1, 0.5, 0.9], lookback=10):
"""训练多个分位数模型"""
# 准备数据
X, y = self.prepare_features(series, lookback)
# 标准化
X_scaled = self.scaler.fit_transform(X)
# 为每个分位数训练模型
for q in quantiles:
model = GradientBoostingRegressor(
loss='quantile',
alpha=q,
n_estimators=100,
max_depth=3,
random_state=42
)
model.fit(X_scaled, y)
self.models[q] = model
self.lookback = lookback
def predict_interval(self, series, confidence=0.8):
"""预测置信区间"""
# 计算对应的分位数
lower_q = (1 - confidence) / 2
upper_q = 1 - lower_q
# 准备最新数据
recent_data = series[-self.lookback:]
X_input = self.scaler.transform([recent_data])
# 获取分位数预测
predictions = {}
for q in [lower_q, 0.5, upper_q]:
if q in self.models:
predictions[q] = self.models[q].predict(X_input)[0]
else:
# 如果没有对应分位数的模型,使用最接近的
closest_q = min(self.models.keys(), key=lambda x: abs(x - q))
predictions[q] = self.models[closest_q].predict(X_input)[0]
return {
'point_forecast': predictions[0.5], # 中位数作为点预测
'lower_bound': predictions[lower_q],
'upper_bound': predictions[upper_q],
'interval_width': predictions[upper_q] - predictions[lower_q],
'confidence_level': confidence
}
def probabilistic_forecast(self, series, steps=10, confidence=0.8):
"""多步概率预测"""
current_series = series.copy()
forecasts = []
for step in range(steps):
# 预测下一步
pred = self.predict_interval(current_series, confidence)
# 使用中位数作为下一步的输入(也可以使用其他策略)
current_series = np.append(current_series[1:], pred['point_forecast'])
forecasts.append({
'step': step + 1,
**pred
})
return pd.DataFrame(forecasts)
# 使用示例
if __name__ == "__main__":
# 生成示例时间序列数据
t = np.linspace(0, 20, 200)
series = np.sin(t) + 0.1 * np.random.normal(size=len(t)) + 0.05 * t
# 创建预测器
forecaster = ProbabilisticTimeSeriesForecaster()
# 训练模型
forecaster.train_quantile_models(series)
# 进行概率预测
forecasts = forecaster.probabilistic_forecast(series, steps=20, confidence=0.8)
print("概率预测结果:")
print(forecasts.head())
四、如何解释和使用概率预测结果?
结果解释示例
def interpret_probabilistic_forecast(forecast_df):
"""解释概率预测结果"""
latest = forecast_df.iloc[-1]
print("=== 概率预测报告 ===")
print(f"📊 点预测值: {latest['point_forecast']:.2f}")
print(f"📈 预测区间: [{latest['lower_bound']:.2f}, {latest['upper_bound']:.2f}]")
print(f"📏 区间宽度: {latest['interval_width']:.2f}")
print(f"🎯 置信水平: {latest['confidence_level']:.0%}")
# 风险评估
if latest['interval_width'] > 2.0:
print("⚠️ 高风险:预测不确定性很高")
elif latest['interval_width'] > 1.0:
print("🔸 中等风险:预测有一定不确定性")
else:
print("✅ 低风险:预测相对可靠")
# 决策建议
print("\n💡 决策建议:")
print(f"- 基准计划使用: {latest['point_forecast']:.2f}")
print(f"- 保守计划考虑: {latest['lower_bound']:.2f}")
print(f"- 乐观计划考虑: {latest['upper_bound']:.2f}")
# 使用解释函数
# interpret_probabilistic_forecast(forecasts)
实际应用场景
1. 库存管理
# 传统方法:基于单点预测订货
order_quantity = predicted_demand # 可能缺货或积压
# 概率预测方法
if upper_bound - lower_bound > threshold: # 不确定性高
order_quantity = point_forecast + safety_stock # 增加安全库存
else: # 不确定性低
order_quantity = point_forecast # 按预测订货
2. 风险管理
# 计算在险价值 (Value at Risk)
var_95 = lower_bound # 有95%的把握不会低于这个值
worst_case = lower_bound - 2 * (upper_bound - lower_bound) # 极端情况
总结
概率预测的核心价值:
| 方面 | 单点预测 | 概率预测 |
|---|---|---|
| 信息量 | 一个数值 | 完整分布 |
| 不确定性 | 隐藏 | 显式量化 |
| 决策支持 | 有限 | 风险评估+多方案 |
| 可靠性 | 看似精确 | 诚实透明 |
关键要点:
-
从确定到概率:接受世界本质上的不确定性
-
从点到区间:用范围代替单点,用概率代替确定性
-
从预测到决策:不仅告诉你会发生什么,还告诉你有多大的把握
概率预测让我们从"盲目相信一个数字"转变为"基于完整信息做出稳健决策",这是数据科学成熟度的重要标志!
更多推荐



所有评论(0)