神经网络游乐场·

让网络把两种颜色分开。看一条边界,怎样从数据里学出来。

可搭建 · 可拆解 · 可对照
先试这个

开始训练,观察白色边界怎样围住绿点。保留结果,再把隐藏层减到 0 做对照。

小步 大步
已更新参数0步
准备就绪

网络怎样加工

输入 → 隐藏层 → 输出

隐藏层1点小图,放大看这个神经元
正权重负权重线越粗,权重绝对值越大悬停连线,查看权重数值
每个小图,是一个神经元的“响应地图”

同一个位置,表示同一组输入。每层重新组合这些响应,最后决定分到哪一类。

它学会了吗

底色是网络判断,圆点是真实类别

实时
绿类橙类分类边界

点击任意圆点,核对“真实类别”和“网络判断”。

训练集误分率—
验证集误分率—
此刻

学习过程

训练集用来学,验证集用来看是否学偏

训练集验证集损失衡量预测分数与目标的差距,越低越好。

只改一个条件,再看看

把本次结果留住,作为下一次实验的参照

先训练一会儿,点“留作对照”。
再改隐藏层、激活函数或正则化,
观察边界和验证集表现的差别。

从头再来会保留数据与随机种子,便于重复比较。

看懂一个神经元

它学的是组合方式

每个神经元把输入乘上不同权重,加上偏置,再经过激活函数。训练调整这些参数;图上的小地图,显示它对不同输入的响应。

看懂一次训练

先算差距,再改参数

前向计算给出预测,损失衡量差距,反向传播算出每个参数该怎样调整。学习率决定改多大;一次更新不保证错误率立刻下降。

看懂一个结果

别只盯着训练集

训练损失下降、验证损失持续回升,是过拟合的信号。更深的网络不一定更好;验证集参与选模型和早停,最终评价仍需独立测试集。

实验说明与参考资料

300 个合成样本,按类别分层随机划分训练集与验证集。页面所有预测、错误率和曲线均由当前网络实时计算;这是一项二维分类教学实验,不代表真实科研任务的模型性能。

位置噪声控制坐标扰动的幅度,不是错标样本的比例。小批量采用有放回随机抽样,全批量每个训练样本恰好用一次。坐标先除以 3,再构造平方与乘积特征;隐藏层激活可选,输出固定为 Tanh,标签为 −1 / +1。输出是倾向分数,并非概率。训练目标为平均半平方误差,加上 L2 权重惩罚;“损失”曲线只显示数据误差项。Dropout 对每个样本的隐藏激活独立采样,训练时按保留率缩放,评估和小地图均关闭 Dropout。

“拆开一步”的梯度柱取每个样本的数据损失对各层激活前数值的导数,在样本与神经元上计算均方根,用对数刻度展示,不含 L2 项。柱高比较的是本次计算的梯度信号,不等于各层权重更新量;学习率决定实际更新幅度。早停每 10 步检查一次验证损失,改善阈值为 0.00001,耐心为 400 步。

参考:scikit-learn · 多层感知器 · Google · 训练、验证与测试数据划分 · PyTorch · Dropout

文字版:神经网络游乐场在做什么

这一页是一个真的能训练的神经网络:你决定给它什么数据、搭几层、每层几个神经元、学习率多大,然后按下开始,看那条分类边界怎样从一片混沌里长出来。它最有价值的地方不是「训练成功」,而是让你亲手把它搞坏,看清楚是怎么坏的。

画面上正在发生什么

底色是网络当前的判断,圆点是真实类别。刚开始底色一片random,因为权重是随机初始化的。训练开始后边界逐渐成形,下方两条曲线分别是训练集和验证集上的表现——要盯的是后面那条。中间那些小方块是每个神经元的「响应地图」:同一个位置代表同一组输入,每层都在把上一层的响应重新组合一次。

选「同心圆」这组数据,先把隐藏层减到 0:无论训练多久边界都是一条直线,圆心永远围不住。加回一层神经元,边界立刻能弯。这就是隐藏层的作用——它不是让模型「更强」,而是让模型能表达原本表达不了的形状。

再选「训练好就够了吗」那个实验:少量带噪声的样本,训练集误分率一路降到很低,验证集误分率却在某一刻掉头往上。那个拐点就是过拟合开始的地方,模型从学规律转向了背样本。

什么时候它会骗你

  • 训练集的成绩越好看,越说明不了问题。参数足够多时,网络可以把每个训练点都记住。真正有意义的只有它在没见过的数据上的表现。这一页把两条曲线画在一起,就是为了让这件事没法回避。
  • 学习率调错,症状完全不同。调太大,损失曲线剧烈震荡甚至冲上天;调太小,曲线几乎是平的,看起来像「学不会」,其实只是走得太慢。两种情况的处方相反,先看曲线形状再决定往哪边调。
  • 换一个随机种子,结论可能就变了。神经网络的初始权重是随机的。同样的设置跑两次,边界可能不一样。所以比较两种配置哪个好,至少要各跑几次看稳定性,不能拿单次结果下结论。
  • 验证集用来早停,就不能再当成绩报。你每次根据验证集表现去调参数,验证集的信息就渗进了模型选择。它给出的数字会越来越乐观,最终成绩必须来自一份完全没参与过任何决定的数据。

常见问题

神经网络需要几个隐藏层?
取决于数据的复杂程度。两团分得开的点不需要隐藏层;同心圆、异或这类需要一层;双螺旋这种缠绕结构需要更多层或更多神经元。实践中先从小网络起步,只有在验证集表现确实受限于模型容量时才加深——盲目加深会让训练更难、更容易过拟合。
激活函数为什么不能省?
如果没有激活函数,多层线性变换叠起来仍然等价于一层线性变换,再深的网络也只能画直线。激活函数提供的非线性,才是多层结构有意义的前提。
损失下降了,但误分率不动,是怎么回事?
损失衡量的是预测概率和目标的差距,误分率只看最终判定对不对。模型可能正在把已经判对的样本的概率从 0.6 推向 0.9——损失在降,判定却没变。这通常是正常现象,不必急着改参数。

本页使用 300 个合成教学点,分层划分训练与验证集;所有数值由浏览器内的模型实时计算,验证集不作为独立测试成绩。

作者与维护:覃秉丰 · 关于覃秉丰 · 引用本页讲解

继续学习