序列建模实战
本节定位
前两节你已经理解了:
- RNN 在“边读边记”
- LSTM / GRU 在“更聪明地控制记忆”
这一节要把这些概念真正落到一个小项目上:
给一段序列,预测后面的值。
学习目标
- 学会把连续序列切成训练样本
- 用 LSTM 搭一个最小时间序列预测器
- 理解训练集、验证集和预测流程
- 学会判断模型是在学规律还是在瞎记
- 知道序列实战里最常见的坑是什么
一、为什么选“时间序列预测”来做实战?
1.1 因为它最适合练序列建模的基本功
很多序列任务都可以抽象成:
- 前面一段输入
- 后面一个输出
时间序列预测就是最典型的例子。
比如:
- 根据过去 7 天销量,预测第 8 天销量
- 根据过去 12 个温度值,预测下一个温度
1.2 一个非常重要的直觉
做这类任务时,模型不是在记单个数字,而是在学:
变化模式。
例如:
- 周期
- 趋势
- 波动
这和普通分类任务很不一样。
二、先造一份可以直接运行的数据
2.1 用正弦波 + 噪声造一个最小序列
这样做的好处是:
- 不依赖外部数据集
- 模式清晰
- 非常适合教学
import numpy as np
import matplotlib.pyplot as plt
np.random.seed(42)
t = np.arange(0, 200)
series = np.sin(t * 0.1) + np.random.randn(200) * 0.05
plt.figure(figsize=(10, 4))
plt.plot(t, series)
plt.title("Toy Time Series")
plt.grid(True, alpha=0.3)
plt.show()
2.2 这串数据长什么样?
它有两个特征:
- 整体是波动的
- 带一点随机噪声
这就比完全规则的序列更接近真实任务一点。
三、滑动窗口:怎么把一整段序列切成样本?
3.1 核心思想
模型不能直接吃“一整条无限序列”。
我们通常会把它切成很多小片段:
- 前
window_size个点作为输入 - 第
window_size + 1个点作为标签
这就叫滑动窗口。
3.2 可运行示例
import numpy as np
series = np.array([1, 2, 3, 4, 5, 6, 7], dtype=np.float32)
window_size = 3
X, y = [], []
for i in range(len(series) - window_size):
X.append(series[i:i + window_size])
y.append(series[i + window_size])
X = np.array(X)
y = np.array(y)
print("X =\n", X)
print("y =", y)
3.3 这一步为什么这么关键?
因为它决定了序列任务的样本定义。
如果窗口构造错了,后面的训练、验证和预测都会跟着错。