机器学习 预测分析

机器学习预测分析实战:时序预测与业务应用

2026-07-11 · 约10分钟阅读 · 时间序列 · LSTM · Prophet · ARIMA · 业务落地

预测分析不是"跑个模型看结果",而是从数据清洗到模型部署的完整闭环。这篇文章记录了我在多个业务项目中落地时序预测的经验,包括数据处理、模型选型、特征工程和生产部署的全过程。

业务场景与数据特征

我做过的时序预测项目主要集中在以下场景:

  • 电商销量预测:某品牌抖音店铺7天销量预测,用于库存备货决策
  • 供应链需求预测:MSD采购量月度预测,减少库存积压
  • 用户行为预测:APP日活用户数预测,用于服务器资源调度

这些场景的共性是:数据具有周期性(日周月)、趋势性(增长或下降)、季节性(节假日波动),以及突发事件(促销活动、爆款单品)的影响。

三种主流方案对比

方案一:Prophet(Meta)

适用场景:具有明显周期性和季节性的业务数据,不需要太复杂的特征工程。Prophet是业务人员入门时序预测的最佳选择

from prophet import Prophet
import pandas as pd

df = pd.read_csv('sales_data.csv')
df = df.rename(columns={'date': 'ds', 'sales': 'y'})

model = Prophet(
    seasonality_mode='additive',
    yearly_seasonality=True,
    weekly_seasonality=True,
    daily_seasonality=False
)

model.add_country_holidays(country_name='CN')

model.fit(df)
future = model.make_future_dataframe(periods=30)
forecast = model.predict(future)

fig = model.plot(forecast)
fig2 = model.plot_components(forecast)
✅ 优点:开箱即用,自动处理节假日,不需要手动提取时间特征,预测结果直观。适合业务分析人员快速上手。
⚠️ 缺点:对非线性趋势和突发事件的捕捉能力有限。如果数据中有促销活动等特殊事件,需要手动添加额外的回归因子。

方案二:ARIMA/SARIMA(统计方法)

适用场景:数据符合平稳性假设,需要解释模型的统计意义。ARIMA是经典的统计时序方法,在金融、经济领域应用广泛。

from statsmodels.tsa.statespace.sarimax import SARIMAX
from statsmodels.tsa.stattools import adfuller

result = adfuller(data['sales'])
print(f'ADF统计量: {result[0]}')
print(f'p值: {result[1]}')

model = SARIMAX(
    data['sales'],
    order=(1, 1, 1),
    seasonal_order=(1, 1, 1, 7)
)
result = model.fit()
forecast = result.get_forecast(steps=14)

predicted_mean = forecast.predicted_mean
conf_int = forecast.conf_int()
✅ 优点:模型具有统计解释性,可以分析趋势、季节性和残差。适合需要向业务方解释"为什么预测值是这样"的场景。
⚠️ 缺点:需要手动选择p、d、q参数,数据必须经过平稳性检验,处理非线性关系能力弱。

方案三:LSTM(深度学习)

适用场景:数据量大、模式复杂、需要捕捉长期依赖关系。LSTM是处理时序数据的深度学习利器,但入门门槛较高。

import numpy as np
from tensorflow.keras.models import Sequential
from tensorflow.keras.layers import LSTM, Dense, Dropout

def create_dataset(data, look_back=7):
    X, Y = [], []
    for i in range(len(data) - look_back):
        X.append(data[i:(i + look_back), :])
        Y.append(data[i + look_back, 0])
    return np.array(X), np.array(Y)

look_back = 7
train_X, train_y = create_dataset(train_data, look_back)
test_X, test_y = create_dataset(test_data, look_back)

model = Sequential()
model.add(LSTM(50, return_sequences=True, input_shape=(look_back, n_features)))
model.add(Dropout(0.2))
model.add(LSTM(50, return_sequences=False))
model.add(Dropout(0.2))
model.add(Dense(25))
model.add(Dense(1))

model.compile(optimizer='adam', loss='mean_squared_error')
history = model.fit(train_X, train_y, batch_size=32, epochs=100, validation_split=0.1)
✅ 优点:可以自动学习复杂的非线性模式,捕捉长期依赖关系,适合处理大规模数据。
⚠️ 缺点:需要大量数据训练,模型不可解释,调参复杂,生产部署成本高。

生产环境的特征工程

时序预测的关键不在模型,而在特征。我总结了一套可复用的特征工程流程:

  1. 时间特征:year, month, day, weekday, is_weekend, hour(如果是小时级数据)
  2. 滚动统计:7天均值、14天均值、7天标准差、环比增长率
  3. 滞后特征:前1天、前7天、前14天、前30天的目标值
  4. 节假日特征:是否节假日、节假日前后天数
  5. 外部特征:促销活动标记、天气数据(如果相关)、竞品数据
import pandas as pd

def create_time_features(df):
    df = df.copy()
    df['year'] = df['ds'].dt.year
    df['month'] = df['ds'].dt.month
    df['day'] = df['ds'].dt.day
    df['weekday'] = df['ds'].dt.weekday
    df['is_weekend'] = (df['ds'].dt.weekday >= 5).astype(int)
    return df

def create_rolling_features(df, target_col='y', windows=[7, 14, 30]):
    df = df.copy()
    for window in windows:
        df[f'{target_col}_rolling_mean_{window}'] = df[target_col].rolling(window=window).mean()
        df[f'{target_col}_rolling_std_{window}'] = df[target_col].rolling(window=window).std()
        df[f'{target_col}_rolling_max_{window}'] = df[target_col].rolling(window=window).max()
    return df

def create_lag_features(df, target_col='y', lags=[1, 7, 14, 30]):
    df = df.copy()
    for lag in lags:
        df[f'{target_col}_lag_{lag}'] = df[target_col].shift(lag)
    return df

模型评估与业务验证

预测模型不能只看RMSE,必须结合业务场景验证。我通常从三个维度评估:

  1. 统计指标:RMSE、MAE、MAPE(平均绝对百分比误差)
  2. 方向准确率:预测趋势与实际趋势一致的比例
  3. 业务指标:预测结果用于决策后带来的收益(如库存成本降低、缺货率下降)
def mean_absolute_percentage_error(y_true, y_pred):
    return np.mean(np.abs((y_true - y_pred) / y_true)) * 100

def directional_accuracy(y_true, y_pred):
    actual_direction = np.diff(y_true) > 0
    predicted_direction = np.diff(y_pred) > 0
    return np.mean(actual_direction == predicted_direction) * 100

生产部署策略

模型训练好只是第一步,如何让预测结果真正服务业务?我总结了三种部署模式:

模式一:定时批处理(推荐)

每天凌晨定时运行预测任务,生成未来7-30天的预测值,存入数据库,供业务系统调用。

import schedule
import time

def run_daily_prediction():
    model = load_model('sales_model.h5')
    data = fetch_latest_data()
    features = preprocess(data)
    predictions = model.predict(features)
    save_predictions(predictions)
    send_alert_if_anomaly(predictions)

schedule.every().day.at('02:00').do(run_daily_prediction)

while True:
    schedule.run_pending()
    time.sleep(60)

模式二:实时API服务

将模型封装成REST API,业务系统按需调用。适合预测频率高、实时性要求强的场景。

from fastapi import FastAPI
from pydantic import BaseModel

app = FastAPI()

class PredictionRequest(BaseModel):
    start_date: str
    end_date: str
    store_id: str

@app.post("/predict")
async def predict(request: PredictionRequest):
    features = build_features(request)
    predictions = model.predict(features)
    return {"predictions": predictions.tolist()}

实际项目踩的坑

坑一:数据泄露。使用未来信息训练模型是最常见的错误。比如用当天的天气数据预测当天的销量,而实际上预测时是不知道当天天气的。

坑二:过度拟合。训练集上表现完美,验证集上一塌糊涂。解决方案:添加Dropout层、减少模型复杂度、增加训练数据、使用早停法(Early Stopping)。

坑三:不处理异常值。促销活动导致的数据峰值会严重影响模型。解决方案:标记异常点、使用鲁棒损失函数(如Huber Loss)、单独处理促销场景。

坑四:预测区间不考虑。只给单点预测值,业务方无法判断置信度。解决方案:输出预测区间(Prophet和SARIMA都支持),让业务方根据置信度做决策。

总结

时序预测的核心是"数据质量 + 特征工程 + 模型选择"的组合。对于大多数业务场景,Prophet是性价比最高的起点——用最少的代码获得合理的预测结果。当Prophet的表现达不到业务要求时,再考虑引入LSTM等深度学习方案。

记住:预测模型不是银弹,它只是业务决策的辅助工具。好的预测系统需要持续监控、定期重新训练,并结合业务人员的经验进行调整。

🤖
AI助手
ONLINE