经典神经网络结构学习笔记

经典神经网络结构学习笔记:CNN、RNN及常见模块

执行摘要(≤200字):本文是一份面向"有一定机器学习基础但非专家"的学习笔记,系统梳理经典神经网络结构:CNN 与 RNN(含常见变体)及若干关键模块(归一化、残差、注意力、可分离/膨胀卷积等)。内容覆盖直观解释与必要数学表达,配合示例、伪代码与结构示意图,最后给出两套可照搬的教学级训练流程(CNN 图像分类、LSTM 序列建模)、对比表格与调试清单,帮助你把"会用"提升到"懂原理、能排错、能改结构"。

概述

神经网络(neural network)可以把它理解为一个可微分(differentiable)的函数族:输入是数据 (x),输出是预测 (\hat{y}),中间由多层"线性变换 + 非线性"叠加构成,参数记为 (\theta)。训练的核心是:定义损失函数 ( \mathcal{L}(\hat{y}, y) ),用梯度下降类方法最小化期望损失,从而让模型在未见数据上也能"泛化"(generalization)。

从计算图角度看,前向传播(forward)把数据一路计算到损失;反向传播(backpropagation)利用链式法则把损失对参数的梯度逐层传回去。深度学习的很多"结构创新",本质上是在让梯度更好流动、让表示更高效(更少参数/更低计算)或让训练更稳定。

学习范式上,常会把任务分为三类(这里只做"足够用"的区分):

监督学习(supervised learning):训练样本带标签 (y),如图像分类(猫/狗)、语音识别(音频→文字)、序列标注(每个词的实体类别)。优化目标直接由标签定义(交叉熵、MSE 等)。

无监督学习(unsupervised learning):没有显式标签,目标是建模数据分布或学表示,如聚类、降维、自编码器、对比学习等。很多现代方法会把无监督/自监督当作"先学通用表示,再用少量标签微调"。

强化学习(reinforcement learning):智能体在环境中交互,得到奖励 (r),目标是最大化长期累计回报。和监督学习不同,奖励往往稀疏且延迟,训练信号来自策略与环境反馈回路。

本节小结:把神经网络先当作"可微函数 + 梯度优化"的统一框架;后续 CNN/RNN/注意力等结构差异,主要体现在"信息如何流动(空间或时间)""参数如何共享""梯度如何稳定"。

CNN

卷积神经网络(CNN, Convolutional Neural Network)专门擅长处理网格状数据 ,尤其是二维图像。它的核心归纳偏置(inductive bias)是:局部相关 + 平移等变/近似不变 + 参数共享。这让它在视觉任务中非常高效。

卷积运算的直观理解与数学表达

直观上,卷积可以看成"一个小窗口(卷积核)在图像上滑动",在每个位置做"局部加权求和",输出一张新的特征图(feature map)。这一操作像是在检测某种局部模式:边缘、纹理、角点,再到更高层的形状与语义。

数学上,深度学习实现里常用的是互相关(cross-correlation)形式(不翻转核),但习惯上仍称"卷积"。对输入 (X \in \mathbb{R}^{H\times W})、卷积核 (K \in \mathbb{R}^{k\times k}),输出 (Y) 的一个位置 ((i,j)) 可写作:

Y_{i,j} = \\sum_{u=0}^{k-1}\\sum_{v=0}^{k-1} K_{u,v}; X_{i+u,; j+v}

多通道情形(RGB 等)则在通道维度再求和;多输出通道对应多组核。这样的权重共享使参数量不随输入尺寸线性膨胀。 citeturn0search0turn5search8

卷积层常见的"几何超参数"包括:
步幅 stride (窗口每次移动几格)、填充 padding (边界补零或其它方式)、膨胀 dilation(核元素之间插空扩大感受野)。输出尺寸的常用计算式(以 1D 表达更直观,2D 对 H/W 分别套用):

\\text{out} = \\left\\lfloor \\frac{\\text{in} + 2p - d\\cdot (k-1) - 1}{s} \\right\\rfloor + 1

这条式子在你做网络"算形状"与排查维度错误时非常实用。

下面是一个非常简化的 ASCII 示意(单通道、stride=1):

text 复制代码
输入X:            卷积核K:        输出Y(局部加权和):
[a b c d]         [k1 k2]         [a*k1+b*k2, b*k1+c*k2, c*k1+d*k2]

(真实 CNN 是 2D/3D 张量,原理一致。)

关键模块:卷积层、池化层、激活函数、批归一化、残差连接

卷积层(convolution layer):提取局部特征并逐层组合。早期 CNN(如 LeNet)已包含"卷积+下采样+非线性+全连接"的雏形。

池化(pooling)/下采样:常见有最大池化(max pooling)与平均池化(avg pooling)。作用是降低分辨率、减少计算、扩大有效感受野,并带来一定平移不变性。代价是细粒度位置信息会损失,因此在检测/分割里往往需要"跳跃连接或上采样"去补回空间细节。

激活函数(activation function):引入非线性。ReLU(rectified linear unit)之所以在 CNN 中常用,是因为它在正半轴不饱和,有助于梯度传播与更快收敛;经典大规模 CNN 中也明确采用了非饱和激活以加速训练。

批归一化(batch normalization, BN):对每个 mini-batch 的中间激活做标准化,再用可学习的缩放/平移恢复表达能力。它能缓解训练中层输入分布变化带来的困难,使更高学习率与更不敏感的初始化成为可能,并经常带来正则化效应。

残差连接(residual / skip connection):把输入 (x) 直接加到某个变换 (F(x)) 的输出上,形成 (y = F(x)+x)。这种结构显著缓解"更深网络更难优化"的问题,使非常深的网络可训练。

text 复制代码
残差块(简化):
   x ────────┐
    │        │
    │      (+)──> y
    v        ^
  [Conv-BN-ReLU]
    v
  [Conv-BN]
    v
   F(x) ─────┘

{"layout":"carousel","aspect_ratio":"16:9","query":["CNN convolution kernel feature map illustration","ResNet residual block diagram","Inception module architecture diagram","depthwise separable convolution diagram"],"num_per_query":1}

常见 CNN 架构:设计动机、结构要点、优缺点

这里按"历史动机"来理解会更稳:从"能跑"→"能在大数据上跑"→"能更深"→"能更高效/更轻量"

LeNet:面向手写数字/文档识别等早期任务的经典 CNN。特点是结构较浅,卷积与下采样交替,最后接全连接分类。优点是思想完整、易理解;缺点是容量有限,不适合复杂自然图像。参数规模通常在"几万级"量级。

AlexNet:把 CNN 推到大规模视觉分类舞台的代表作之一。关键点包括更深更宽的网络、使用非饱和激活、利用 dropout 抑制全连接层过拟合,以及在大数据集上训练取得显著提升。优点是证明"更深更大 + 合理训练技巧"有效;缺点是全连接层参数巨大、计算与内存开销高,结构相对"粗放"。

VGG :核心动机是用大量 3×3 小卷积核堆叠来增加深度,用统一的模块化设计替代大核卷积。优点是结构规则、易复现、特征通用性强;缺点是参数量与计算量都很大,尤其全连接层负担重。

ResNet:动机是解决"网络变深后出现的优化困难/退化现象",用残差学习框架让梯度更易通过深层结构传播。优点是可训练极深网络、泛化优秀、成为许多视觉系统的事实基础骨干;缺点是结构更复杂,推理时仍有一定计算成本(但通常比同等精度的"纯堆叠"更划算)。

Inception(GoogLeNet/Inception 系列):动机是提高计算资源利用率,在同一层里并行多尺度卷积(如 1×1、3×3、5×5)并做拼接,同时大量使用 1×1 卷积做降维(bottleneck)以压缩计算。优点是参数更省、表达多尺度;缺点是模块设计更"手工",实现与调参复杂度高于 VGG。

MobileNet :动机是面向移动端/嵌入式的低延迟与低功耗;核心手段是深度可分离卷积(depthwise separable convolution),把标准卷积拆成"逐通道空间卷积 + 1×1 点卷积",显著降低计算与参数,并通过少量超参数在精度与速度间权衡。优点是轻量高效;缺点是容量受限,对训练细节更敏感。

为了更直观,你可以把这些架构的"核心取舍"概括为一句话:

LeNet:把想法跑通;AlexNet:把规模做大并加入训练技巧;VGG:用规则堆叠换性能;ResNet:用残差让更深可训练;Inception:用多分支多尺度提高效率;MobileNet:用结构分解换低成本。

典型应用与计算流程示例:分类、检测、分割

图像分类(image classification):输入整张图 → 输出类别概率。典型流程:卷积堆叠提特征 → 全局池化/全连接 → softmax。

分类的伪代码(教学级):

pseudo 复制代码
# 输入: 图片 x, 标签 y
# 模型: CNN backbone + classifier head

logits = Model(x)                 # [B, C]
loss   = CrossEntropy(logits, y)

loss.backward()                   # 反传梯度
optimizer.step()                  # 更新参数
optimizer.zero_grad()

目标检测(object detection):输出每个目标的类别 + 边界框。你可以把检测理解为"分类 + 定位"的组合。两条经典路线:

  • 两阶段(two-stage):先产生候选区域(proposal),再对每个候选做分类与边框回归,如 Faster R-CNN:RPN 共享卷积特征并生成 proposals,再进入 RoI 级别的分类/回归头。优点是精度高、对小目标更友好;缺点是结构复杂、推理相对慢。 citeturn1search3
  • 一阶段(one-stage):直接在密集网格上回归边界框并预测类别,如 YOLO 把检测视为回归问题,端到端一次前向得到所有框与类别。优点是快;缺点是某些场景下更难兼顾召回与定位精度(不同版本差异很大,这里只抓"大方向")。

检测(两阶段)计算流程示意:

text 复制代码
Image
  |
Backbone CNN  ---> Feature Map
  |                    |
  |                  RPN  ----> Proposals (RoIs)
  |                    |
  +---- shared --------+
                        |
                      RoI Align/Pool
                        |
                Classifier + Box Regressor
                        |
                boxes + class scores

语义分割(semantic segmentation):对每个像素做分类,输出与输入同分辨率的类别图。经典演进:

  • FCN:把分类网络"卷积化",用上采样与跳跃连接融合深层语义与浅层细节,实现端到端像素预测。
  • U-Net:编码器-解码器对称结构,跳跃连接把高分辨率特征传给解码端,强调精确定位与数据增强的训练策略。
  • DeepLab:强调空洞/膨胀卷积(atrous/dilated convolution)与多尺度上下文(如 ASPP)来提升密集预测表现,并通过后处理/结构组合改善边界。

分割(FCN/U-Net 风格)流程示意:

text 复制代码
Input -> Encoder(下采样提语义) -> Bottleneck -> Decoder(上采样还原分辨率) -> Pixel-wise logits
                   |---------------------------------------------|
                              skip connections(细节融合)

常见实现细节与训练技巧

这部分非常"工程",但恰恰决定你能否稳定复现效果。

初始化(initialization)

  • 若激活函数偏饱和(如 sigmoid/tanh),常用保持方差稳定的初始化思想(如 Xavier/Glorot)。
  • 若使用 ReLU/其变体,常用针对 rectifier 的初始化(He init)以更好保持信号/梯度尺度。

优化器与学习率(learning rate)

  • Adam 往往更"省心",对稀疏梯度与非平稳目标表现好;但在某些视觉任务里,SGD+动量+合适学习率计划仍很强。Adam 的设计基于一阶梯度的自适应矩估计。
  • BN 往往允许更高学习率并降低对初始化敏感度,但也会引入"训练/推理模式不同"的注意点(running mean/var)。

正则化(regularization)

  • Dropout 通过训练时随机丢弃部分神经元,打破共适应,缓解过拟合;常见于全连接层或注意力/MLP 子层。
  • 权重衰减(L2/weight decay)、早停(early stopping)、数据增强都属于常用正则手段。

数据增强(data augmentation)

  • 经典分类中大量使用随机裁剪、水平翻转等增强来提升泛化;在某些分割任务中,强数据增强被明确当作"用少标注训练好模型"的关键策略之一。

本节小结:CNN 的"强项"来自局部连接与权重共享;训练上,BN/残差/合适初始化与学习率策略共同决定了你能否把网络堆深、堆稳;应用上,分类-检测-分割可以理解为"输出结构逐渐变密集"。

RNN

循环神经网络(RNN, Recurrent Neural Network)擅长建模序列(sequence):文本、语音帧、时间序列传感器数据等。它的核心思想是:用隐藏状态 (h_t) 把"过去信息"压缩进一个向量,并在时间上递推。

基本结构、时间展开与梯度消失/爆炸

最基础的 RNN 可以写成:

h_t = \\phi(W_{xh}x_t + W_{hh}h_{t-1} + b_h), \\quad \\hat{y}*t = \\psi(W* {hy}h_t + b_y)

其中 (x_t) 是第 (t) 步输入,(\phi) 是非线性(tanh/ReLU 等),(\psi) 视任务而定(softmax、线性回归等)。训练时通常使用时间反向传播(BPTT, backpropagation through time):把网络在时间上展开成一个深层计算图,再做反向传播。

RNN 的经典难点是长程依赖(long-term dependency):当依赖跨很多时间步时,梯度在反传过程中会出现指数级衰减(消失)或增长(爆炸),导致训练不稳定或学不到远距离信息。该问题在早期工作中被系统分析,并在后续工作中提出了如梯度裁剪(gradient clipping)等实用缓解策略。

一个"时间展开"示意(把同一组参数重复使用):

text 复制代码
t=1      t=2      t=3      ...     t=T
x1 ---> [RNN] --> [RNN] --> [RNN] --------> 
          |         |         |
         h1        h2        h3        ... hT

LSTM、GRU:门控机制与数学推导(足够用的版本)

为解决长程依赖,经典做法是引入门控(gating):用可学习的"阀门"控制信息写入、保留、输出,从而让梯度在某些通道上更稳定地流动。

LSTM(long short-term memory)

LSTM 的关键是引入细胞状态 (c_t)(可以看作长期记忆通道)以及门:遗忘门 (f_t)、输入门 (i_t)、输出门 (o_t)。常见公式(以 sigmoid (\sigma) 与 tanh 为例):

\\begin{aligned} f_t \&= \\sigma(W_f\[x_t, h_{t-1}\] + b_f) \\ i_t \&= \\sigma(W_i\[x_t, h_{t-1}\] + b_i) \\ \\tilde{c}*t \&= \\tanh(W_c\[x_t, h* {t-1}\] + b_c) \\ c_t \&= f_t \\odot c_{t-1} + i_t \\odot \\tilde{c}*t \\ o_t \&= \\sigma(W_o\[x_t, h* {t-1}\] + b_o) \\ h_t \&= o_t \\odot \\tanh(c_t) \\end{aligned}

这里 (\odot) 是逐元素乘法。LSTM 的贡献在于:(c_t) 的递推包含了一条"近似线性"的路径(乘以 (f_t) 并加上新信息),使误差信号可以在较长时间跨度上传递。 citeturn2search0turn2search12

一个很实用的"推导视角":看 (c_t) 对 (c_{t-1}) 的偏导

\\frac{\\partial c_t}{\\partial c_{t-1}} = f_t

当遗忘门 (f_t \approx 1) 时,梯度通过细胞状态几乎不衰减;当 (f_t \approx 0) 时,模型选择"忘掉"过去。这就是门控让"记/忘"可学习的本质。后来工作进一步强调了"遗忘门"的重要性,使 LSTM 在连续流式输入中能学会在合适时机重置记忆。 citeturn2search1turn2search17

GRU(gated recurrent unit)

GRU 可以看成对 LSTM 的简化:合并了部分门与状态结构,常见写法:

\\begin{aligned} z_t \&= \\sigma(W_z\[x_t, h_{t-1}\] + b_z) \\quad \\text{(更新门)}\\ r_t \&= \\sigma(W_r\[x_t, h_{t-1}\] + b_r) \\quad \\text{(重置门)}\\ \\tilde{h}*t \&= \\tanh(W_h\[x_t, r_t \\odot h* {t-1}\] + b_h)\\ h_t \&= (1-z_t)\\odot h_{t-1} + z_t \\odot \\tilde{h}_t \\end{aligned}

更新门 (z_t) 决定"保留旧状态 vs 写入新状态"的比例;重置门 (r_t) 决定用多少过去信息来生成候选状态。GRU 在机器翻译的编码器-解码器框架中被提出并验证有效。 citeturn2search2turn2search6

LSTM vs GRU:怎么理解优劣

在实践中你常会看到:

  • GRU 参数更少、结构更紧凑,训练/推理可能更快;
  • LSTM 表达更灵活(显式 (c_t) 通道),在某些长依赖任务上更稳。

但更关键的经验是:差异常由数据规模、序列长度分布、正则/初始化/学习率等训练细节放大或缩小,所以建议把它们当作两个"强基线",以验证为准。 citeturn2search2turn2search0turn5search8

双向RNN、堆叠RNN、注意力与Transformer的关系(简要过渡)

双向 RNN(bidirectional RNN):对同一序列同时做正向与反向递推,把两个方向的隐藏状态拼接/融合,用于需要"同时看前后文"的任务(如序列标注、语音帧分类等)。其经典形式在早期论文中被系统讨论。 citeturn5search11turn5search7

堆叠 RNN(stacked RNN):把多层 RNN 叠起来,上层以更抽象的时间特征为输入,类似 CNN 的"层级表示"。深层结构带来表达能力,也带来更难训练,需要更强的正则与梯度稳定技巧。 citeturn5search8turn5search6

注意力机制(attention):在编码器-解码器翻译中,注意力提出了一个关键观点:不要把整句输入压成一个固定向量,而是让解码器在每一步"软对齐"并选择更相关的输入片段。这样能缓解长句信息瓶颈,并产生可解释的对齐权重。 citeturn3search0turn3search4

Transformer:进一步把"注意力"推广为核心计算单元,提出仅基于注意力的序列到序列结构,去掉循环与卷积,从而获得更强的并行训练能力,并引入自注意力(self-attention)与位置编码(positional encoding)来建模序列顺序。 citeturn3search1turn3search5

你可以把这条脉络记成:"RNN 通过递推传信息;注意力让信息在序列位置间直接'跳转';Transformer 把这种'跳转'变成主干计算范式"。 citeturn3search0turn3search5

典型应用与流程示例:序列标注、机器翻译、语音识别

序列标注(sequence labeling):输入为词/字序列,输出为每个位置的标签(如词性、实体类别)。常用结构:Embedding → BiLSTM/GRU → 逐位置分类头(可结合 CRF,这里不展开)。 citeturn5search11turn2search0

伪代码(以逐位置 softmax 为例):

pseudo 复制代码
tokens = Tokenize(sentence)
emb    = Embedding(tokens)              # [T, D]
h      = BiRNN(emb)                     # [T, H*2]
logits = Linear(h)                      # [T, num_tags]
loss   = Sum_t CrossEntropy(logits[t], tag[t])

citeturn5search11turn5search8

机器翻译(machine translation):经典路线是 Encoder-Decoder:编码器读入源句,解码器生成目标句;引入注意力后,解码器每一步能对源句位置加权,从而提升翻译质量,尤其对长句更有效。 citeturn3search0turn2search2

注意力版 Seq2Seq 的计算流程(高度简化):

text 复制代码
source tokens -> Encoder RNN -> {h_1, h_2, ..., h_T}
                                 |
target step t: Decoder state s_t |
          attention(s_t, {h_i}) -> context c_t
          [s_t, c_t] -> predict y_t

citeturn3search0turn2search2

语音识别(speech recognition):把连续声学特征序列映射为文字序列,是典型长序列建模问题。RNN/LSTM 长期是重要基线(不涉及更复杂的 CTC/Transducer 细节时,可先把它看作"序列到序列 + 对齐问题")。训练难点通常集中在长序列梯度稳定与对齐。 citeturn5search8turn5search6

训练技巧与常见问题要点

  1. 梯度裁剪(gradient clipping):对梯度范数做上限截断,缓解爆炸梯度,是训练 RNN 的常用"保险丝"。 citeturn5search2turn5search6
  2. 截断 BPTT(truncated BPTT):把超长序列按窗口分段,只反传固定步数,降低显存与时间成本,但会牺牲超长依赖学习。 citeturn5search8turn2search3
  3. padding 与 mask:批处理时把不等长序列补齐,必须用 mask 避免把 padding 当成有效 token;否则会出现"看起来在学但学的是 padding"的怪现象。 citeturn5search8
  4. 归一化选择:BN 在 RNN 上不如在 CNN 上直观,LayerNorm 因为对单个样本/时间步做归一化,通常更适合序列模型稳定训练。 citeturn3search2turn1search2

本节小结:RNN 的本质是"用状态递推压缩历史",难点是长程梯度;LSTM/GRU 用门控让"记/忘"可学习;注意力把信息选择从"隐状态记忆"转为"显式加权读取",并最终发展到 Transformer。 citeturn2search3turn2search0turn2search2turn3search5

其他重要模块与概念

这一节把"经常被当作积木复用"的模块集中解释:它们在 CNN 与 RNN/Transformer 中反复出现,理解它们能显著提升你"读结构图"的速度。

注意力、自注意力、位置编码

**注意力(attention)**可以用一句话概括:给定查询(query),在一组键值对(key/value)上计算相关性并加权求和,得到"聚焦后的表示"。在机器翻译中,注意力相当于让解码器每一步选择更相关的源词表示。 citeturn3search0turn3search4

**自注意力(self-attention)**则是:query/key/value 都来自同一序列,从而每个位置都能"看见"其它位置并建立依赖。Transformer 里常用"缩放点积注意力":

\\text{Attention}(Q,K,V)=\\text{softmax}\\left(\\frac{QK\^\\top}{\\sqrt{d_k}}\\right)V

多头注意力(multi-head)则把 (Q,K,V) 投影到多个子空间并行计算,再拼接融合,从而捕获不同类型的关系。 citeturn3search5turn3search1

Transformer 不用递推,因此需要**位置编码(positional encoding)**注入顺序信息。经典做法是把基于正弦/余弦的固定位置向量加到 token embedding 上,使模型能区分"第几个位置"。 citeturn3search5turn3search21

一个 ASCII 结构示意(单层 Transformer Encoder 的核心骨架):

text 复制代码
x + PosEnc
   |
[Multi-Head Self-Attention]
   | \
   |  + Residual
   v
 LayerNorm
   |
[FFN]
   | \
   |  + Residual
   v
 LayerNorm

citeturn3search5turn3search2

归一化层、残差/跳跃连接:何时用、为什么有用

BatchNorm(BN):依赖 batch 统计量,训练与推理行为不同;在 CNN 中非常常见,常与卷积配套提升训练速度与稳定性。 citeturn1search2turn1search18

LayerNorm(LN):对单个样本的层内特征做归一化,训练/推理一致,且更容易应用于 RNN/Transformer 的时间维度(每个时间步单独算统计量)。它被提出时就强调了在 RNN 上的适用性与稳定隐藏状态动态的效果。 citeturn3search2turn3search6

残差连接:本质是提供"捷径",让信息与梯度可以绕过部分变换,缓解深层优化困难;在 ResNet 与 Transformer 中都是基础设施。 citeturn0search3turn3search5

你可以用一个调参经验来记:当你发现"加深网络就训练崩/收敛极慢",优先检查是否缺少(或使用不当)残差与归一化。 citeturn0search3turn1search2turn3search2

可分离卷积与膨胀卷积:原理、何时使用、示例

深度可分离卷积(depthwise separable convolution):把标准卷积分解为两步:

  1. Depthwise:每个输入通道单独做 (k\times k) 空间卷积;
  2. Pointwise:用 1×1 卷积把通道混合起来。

这种分解显著减少乘加运算与参数,成为轻量网络的重要基石。 citeturn1search1turn11view2

text 复制代码
标准卷积:      (k×k×Cin) -> Cout
Depthwise:     k×k×Cin  (逐通道)
Pointwise:     1×1×Cin  -> Cout (通道融合)

citeturn1search1

膨胀/空洞卷积(dilated/atrous convolution):在卷积核元素间插入间隔,使感受野在不增加参数/不降分辨率的情况下扩大,非常适合密集预测(分割)中获取更大上下文。相关工作指出它能系统聚合多尺度上下文而不损失覆盖;并在分割系统里被作为关键工具用于控制特征响应的分辨率。 citeturn6search2turn6search1

一个 3×3 的膨胀卷积(d=2)示意("X"为采样点):

text 复制代码
X . X . X
. . . . .
X . X . X
. . . . .
X . X . X

citeturn6search2

何时用?

  • 你想要更大上下文但不想继续下采样(例如分割边界需要细节)→ 考虑膨胀卷积/ASPP。 citeturn6search1turn6search2
  • 你被算力/延迟/参数限制卡住(移动端、实时)→ 考虑深度可分离卷积或 MobileNet 类骨干。 citeturn1search1turn11view2

本节小结:注意力把"信息选择"显式化;位置编码补回顺序;BN/LN/残差是稳定训练的三大基建;可分离卷积强调效率,膨胀卷积强调在密集预测里扩大感受野。 citeturn3search5turn3search2turn1search2turn1search1turn6search2

实践部分

这一节给两套"从数据到训练到评估"的完整教学示例,你可以把它们当作自己的项目模板(把数据集与模型替换即可)。

教学示例一:基于 CNN 的图像分类训练流程

任务设定:多分类图像分类(例如 10 类物体)。目标是训练一个 CNN,使 Top-1 准确率尽可能高。 citeturn0search1turn5search8

数据预处理(data preprocessing)

  1. 划分 train/val/test(至少保留验证集用于调参与早停)。 citeturn5search8
  2. 统一尺寸(若原图大小不一):可 resize 到固定分辨率;或训练时随机裁剪,验证/测试用中心裁剪。 citeturn8search0
  3. 数值归一化:把像素缩放到 ([0,1]) 或标准化到零均值/单位方差(使用与训练权重一致的预处理尤重要)。 citeturn8search0
  4. 数据增强:随机翻转、随机裁剪、轻微颜色扰动等(训练用,验证不用)。 citeturn0search1turn6search0

模型定义(伪代码):这里以"小型 ResNet 风格分类器"为例(残差块 + 全局平均池化)。残差思想来自深残差学习框架,BN 用于稳定训练。 citeturn0search3turn1search2

pseudo 复制代码
class SmallResNetClassifier:
    stem: Conv(3->C, 3x3) + BN + ReLU
    stage1: repeat N1 times { ResidualBlock(C) }
    stage2: repeat N2 times { ResidualBlock(2C, downsample=True) }
    stage3: repeat N3 times { ResidualBlock(4C, downsample=True) }
    head: GlobalAvgPool + Linear(4C -> num_classes)

ResidualBlock(ch, downsample=False):
    if downsample:
        shortcut = Conv1x1(stride=2) + BN
        main = Conv3x3(stride=2)+BN+ReLU + Conv3x3+BN
    else:
        shortcut = identity
        main = Conv3x3+BN+ReLU + Conv3x3+BN
    return ReLU(main + shortcut)

citeturn0search3turn1search2

训练循环(training loop):推荐先从"可稳定收敛"的默认组合开始:交叉熵损失 + Adam 或 SGD 动量 + 学习率计划 + 早停/保存最优。 citeturn4search1turn5search8turn4search0

pseudo 复制代码
for epoch in range(E):
    model.train()
    for (x, y) in train_loader:
        x = augment_and_normalize(x)
        logits = model(x)
        loss = cross_entropy(logits, y)

        optimizer.zero_grad()
        loss.backward()
        clip_grad_if_needed()          # 训练不稳时启用
        optimizer.step()

    model.eval()
    val_metrics = evaluate(model, val_loader)
    scheduler.step(val_metrics or epoch)
    save_best_checkpoint_if_improved(val_metrics)

citeturn4search1turn5search8turn5search6

常见调参建议(从高性价比到低性价比)

  • 先调学习率与 batch size(很多"不收敛"本质是 LR 不合适)。BN 往往允许更高 LR。 citeturn1search2turn5search8
  • 过拟合时优先加数据增强、权重衰减、dropout(尤其全连接/分类头)。 citeturn4search0turn6search0turn5search8
  • 深度不够→换更强骨干(如从 VGG 风格到 ResNet 风格),但要配套残差与归一化。 citeturn0search2turn0search3turn1search2
  • 受限于算力/延迟→换轻量骨干(MobileNet 系列),并适当降低输入分辨率或通道宽度。 citeturn1search1turn11view2

评估指标与结果分析

  • Top-1 accuracy:最常用;也可看 Top-5(类别多时)。 citeturn10view0
  • 混淆矩阵:定位"哪些类互相容易混"。 citeturn5search8
  • 训练/验证曲线:判断是否过拟合(train↑ val↓/停滞)或欠拟合(两者都低)。 citeturn5search8turn4search0

本示例小结:分类任务要把握"三件套":稳定的骨干结构(残差+BN)、可靠的数据预处理/增强、合理的 LR/正则。你能把这些跑顺,就能把大多数 CNN 分类实验复现到一个可信水平。 citeturn0search3turn1search2turn6search0turn5search8

教学示例二:基于 RNN/LSTM 的序列建模流程

任务设定:给定序列 (x_{1:T}) 预测标签(序列分类,如情感正负);或预测下一个 token(语言模型/时间序列预测)。下面以"序列分类(文本情感)"为主线,末尾补充"下一个 token"版本。 citeturn5search8turn2search0

数据预处理

  1. 分词/切分(tokenization),构建词表(vocab);把 token 映射到 id。 citeturn5search8
  2. 控制序列长度:截断过长样本、padding 过短样本,并生成 mask。 citeturn5search8
  3. 可选:使用子词(subword)以缓解 OOV(这里不展开原理)。 citeturn3search5

模型定义(伪代码):Embedding → LSTM → 池化/最后一步状态 → 分类头。LSTM 的门控与遗忘门机制是其关键。 citeturn2search0turn2search1

pseudo 复制代码
class LSTMSequenceClassifier:
    emb = Embedding(vocab_size, d_model)
    lstm = LSTM(input_size=d_model, hidden_size=H, num_layers=L, bidirectional=True/False)
    head = Linear(H*(2 if bidirectional else 1) -> num_classes)

forward(tokens, mask):
    E = emb(tokens)                     # [B, T, d_model]
    Hs = lstm(E, mask)                  # [B, T, H*dir]
    h = Pool(Hs, mask)                  # e.g., take last valid state or masked mean
    logits = head(h)                    # [B, C]
    return logits

citeturn2search0turn5search11

训练循环:核心不同点在于序列长度与 mask;以及必要时做梯度裁剪以防爆炸梯度。 citeturn5search2turn5search6turn4search1

pseudo 复制代码
for epoch in range(E):
    model.train()
    for (tokens, mask, y) in train_loader:
        logits = model(tokens, mask)
        loss = cross_entropy(logits, y)

        optimizer.zero_grad()
        loss.backward()
        clip_grad_norm(model, max_norm=1.0)
        optimizer.step()

citeturn5search6turn4search1

调参建议

  • 若训练非常不稳:先开梯度裁剪;再减学习率;再检查 padding/mask 是否正确。 citeturn5search6turn5search8
  • 序列太长:用截断 BPTT 或下采样(语音帧)减少 T;或改用注意力/Transformer(更易并行)。 citeturn5search8turn3search5
  • 欠拟合:增大 hidden size、层数或换 BiLSTM;过拟合则加 dropout/权重衰减与更强数据清洗。 citeturn4search0turn5search11turn5search8
  • 归一化:LN 往往比 BN 更直接适配 RNN 动态。 citeturn3search2turn1search2

评估指标与结果分析

  • 分类:accuracy/F1(类别不均衡时尤其关注 F1)。 citeturn5search8
  • 错例分析:查看"长句/否定词/讽刺/领域词"是否导致系统性错误;这往往指向 tokenization、词表覆盖或模型容量问题。 citeturn5search8

扩展:下一个 token 预测(语言模型/时间序列)

把 head 改成对每个时间步输出词表分布,训练目标是预测 (x_{t+1}),常用指标是困惑度(perplexity)。长依赖与梯度问题会更突出,LSTM/GRU 与梯度裁剪更常用。 citeturn2search3turn2search0turn5search6

本示例小结:序列建模最容易踩的坑是 mask/padding 与梯度稳定;把"数据管道正确 + 裁剪/学习率合理 + 选对 LSTM/GRU/BiRNN"三点做好,RNN 类基线就能稳定工作。 citeturn5search6turn5search11turn2search0

常见模型对比表:设计选择、复杂度、参数量、适用场景

下表的参数量与 GFLOPs 采用常用实现/配置的公开统计(不同实现会略有差异,指标用于"量级比较")。 citeturn10view0turn12view0turn11view0turn11view3turn11view2turn13search0

模型/模块 设计选择要点 参数量(典型) 计算复杂度(粗略) 适用场景 主要优点 主要代价/缺点
LeNet 卷积+下采样+全连接的早期范式 ~6万 小图/简单模式 易懂、结构短小 表达能力有限
AlexNet 更深更宽、强数据与训练技巧、dropout ~61.1M ~0.71 GFLOPs 分类/迁移学习基线 推动大规模 CNN 成功 参数大、FC 层重
VGG16 大量 3×3 堆叠、结构规则 ~138.4M ~15.47 GFLOPs 分类、特征抽取 规则、可移植特征强 计算/内存昂贵
ResNet50 残差连接让深层可训练 ~25.6M ~4.09 GFLOPs 分类/检测/分割骨干 精度强、可扩展深度 实现更复杂
GoogLeNet(Inception v1) 多分支多尺度 + 1×1 降维 ~6.6M ~1.5 GFLOPs 分类/骨干网络 参数省、效率高 模块复杂
Inception v3 改进 Inception 模块与分解卷积 ~27.2M ~5.71 GFLOPs 分类/迁移学习 精度与效率折中 结构较"手工"
MobileNet v2 可分离卷积+轻量设计 ~3.5M ~0.3 GFLOPs 移动端/实时 延迟低、模型小 容量较小、细节敏感
LSTM 门控+细胞状态 (c_t) 随 (H,D) 变化:约 (O(H(H+D))) (O(T\cdot H(H+D))) 序列分类/预测 长依赖更稳 难并行、长序列慢
GRU 简化门控、无显式 (c_t) 略少于 LSTM(同 H) 同阶 序列任务强基线 更轻量 某些长依赖任务未必更优
Transformer 自注意力+位置编码+LN+残差 取决于层数与维度 注意力约 (O(T^2\cdot d)) 翻译/大模型/通用序列 并行强、建模全局依赖 长序列 (T^2) 成本高

本节小结:实践上先用"ResNet50 或 MobileNet(受限场景)+规范训练流程"做视觉基线;序列任务先用"LSTM/GRU + 裁剪 + mask 正确"做强基线;对比表的意义是帮你快速判断"参数/计算预算"与"结构选择"的匹配。 citeturn12view0turn11view2turn5search6turn3search5

常见问题与调试指南

下面列出至少 15 条最常见的"症状 → 原因 → 处理策略"。建议你把它当作训练时的排障清单。

  1. 训练损失不下降/几乎不动:常见是学习率太小、初始化不合适或数据/标签管道有错(比如标签错位)。先做"过拟合一个极小 batch"(如 32 张图)验证管道。 citeturn5search8turn4search2turn4search3

  2. 损失变成 NaN/Inf:多见于学习率过大、数值溢出、log(0) 或 softmax 实现不稳。先降 LR;启用梯度裁剪;确认损失实现是数值稳定版。 citeturn5search6turn4search1

  3. 梯度爆炸(尤其 RNN):表现为 loss 抖动剧烈、突然发散。启用 gradient clipping 是最常用补救;必要时减少序列长度或做截断 BPTT。 citeturn5search6turn2search3

  4. 梯度消失/学不到长依赖:RNN 长序列常见。尝试 LSTM/GRU;加入注意力;或改用 Transformer(更直接建模远距离关系)。 citeturn2search3turn2search0turn3search5

  5. 训练集精度很高,验证集很差(过拟合):加数据增强、权重衰减、dropout;减少模型容量;或做早停。 citeturn4search0turn6search0turn5search8

  6. 训练集和验证集都很差(欠拟合):模型容量不足或特征不够。加深/加宽网络,换更强骨干(如从浅 CNN 到 ResNet),或训练更久并调 LR。 citeturn0search3turn5search8

  7. 验证集波动很大:可能是验证集太小、batch 太小导致 BN 统计不稳定,或数据增强在验证集也被误用。固定验证流程、增大验证集或使用 LN/冻结 BN。 citeturn1search2turn3search2turn8search0

  8. 推理时准确率比训练/验证时差很多:常见于忘记切到 eval 模式(BN/Dropout 行为不同),或推理预处理与训练不一致。 citeturn1search2turn4search0turn8search0

  9. 训练很慢/显存爆:输入分辨率过大、batch 太大、模型太重。压分辨率、用混合精度、换轻量骨干(MobileNet),或减少层数/通道。 citeturn1search1turn11view2

  10. 检测/分割定位不准(边界糊、漏小目标):下采样过多会丢空间细节;考虑跳跃连接(FCN/U-Net)或膨胀卷积(DeepLab)保留分辨率与上下文。 citeturn3search3turn6search0turn6search1

  11. 类别不均衡导致只学会预测大类:改用加权损失、重采样,或看更合适指标(F1、mAP/mIoU)。 citeturn5search8turn1search3turn6search1

  12. RNN 输出"被 padding 污染":mask 没用对,padding token 被当成真实输入。检查:loss 只对有效位置计算;池化/取最后状态要"最后有效步"。 citeturn5search8

  13. LSTM/GRU 训练后期不再提升:可能 LR 衰减不合理或正则过强。尝试更平滑的学习率计划;检查 dropout 位置与比例。 citeturn4search0turn5search8

  14. 换了更深网络反而更差:可能是优化困难或超参不匹配;深层结构通常需要残差、归一化与更合适初始化/学习率。 citeturn0search3turn1search2turn4search3

  15. 模型在训练集上也"记不住"(连小样本都过拟合不了):优先怀疑实现 bug:标签错、维度错、loss 用错、数据增强过强、学习率极端。用"极小数据集 + 关掉增强 + 固定随机种子"定位。 citeturn5search8turn6search0

  16. dropout 开了反而更差:可能因为你已经用 BN 或数据增强很强,或 dropout 放在不合适位置(如卷积特征过早丢失)。尝试降低 dropout rate 或只在分类头用。 citeturn1search2turn4search0

  17. BatchNorm 在小 batch 下效果差:BN 依赖 batch 统计,小 batch 噪声大;可换 GroupNorm/LN(此处不展开 GroupNorm),或冻结 BN 统计、使用累积梯度模拟大 batch。BN 的 batch 依赖性与替代动机在 LN 工作中有讨论。 citeturn1search2turn3search2

  18. Transformer 长序列显存/计算爆炸:自注意力复杂度随 (T^2) 增长;缩短序列、分块、稀疏注意力或用 RNN/卷积作为替代(这里仅提示方向)。 citeturn3search5

本节小结:排错优先级建议是:先证数据与训练/推理模式一致 → 再调学习率与梯度稳定 → 再考虑结构升级(残差/归一化/注意力/轻量化)。把"能过拟合小样本"当作最强的管道自检工具。 citeturn5search8turn5search6turn1search2turn0search3turn3search5

总结与学习建议

学习经典结构的目标不是"背网络图",而是形成一套可迁移的理解框架:看见结构就能推断信息流、参数量与训练风险点。CNN 与 RNN 的经典问题(空间局部性 vs 时间递推、深层优化 vs 长程梯度)在后续模型里仍以不同形式出现。 citeturn5search8turn2search3turn0search3turn3search5

一个可执行的学习路线(按"能做出东西"的顺序):

第一阶段:把训练基本功补齐

掌握损失函数、反向传播直觉、初始化与学习率的作用、过拟合与正则化的诊断方法;能从零实现一个小 MLP/CNN 并稳定训练。 citeturn5search8turn4search2turn4search0

第二阶段:CNN 主线(分类→检测→分割)

先用 ResNet/轻量骨干把分类跑到稳定,再理解两阶段检测(RPN + RoI)与一阶段检测(密集回归),最后做 FCN/U-Net/DeepLab 风格分割,把"下采样损细节、上采样补回去"的思想吃透。 citeturn0search3turn1search3turn6search3turn3search3turn6search0turn6search1

第三阶段:RNN 主线(序列分类→Seq2Seq→注意力)

先把 LSTM/GRU 的门控公式与梯度问题搞清楚(裁剪、mask、截断 BPTT),再理解注意力如何缓解固定向量瓶颈,为 Transformer 过渡。 citeturn2search3turn2search0turn5search6turn3search0turn3search5

第四阶段:进阶方向(只给方向,不列出处)

  • Transformer 系列:长序列建模、稀疏/线性注意力、预训练-微调范式。 citeturn3search5
  • 图神经网络(GNN):把卷积/消息传递推广到图结构数据。 citeturn5search8
  • 生成模型:自回归、扩散、对抗生成等(可与 CNN/Transformer 结合)。 citeturn5search8
  • 强化学习:把"感知网络(CNN/Transformer)"与"决策优化"结合,处理延迟奖励与探索。 citeturn5search1turn5search9

推荐练习项目(从易到难、每一步都能产出可展示结果):

做一个小型图像分类器(含增强与可视化错例)→ 做一个小目标检测或简单 YOLO 复现(只需跑通流程)→ 做一个 U-Net 分割项目(强调数据增强与边界误差分析)→ 做一个 BiLSTM 序列标注(mask 正确)→ 做一个注意力版 Seq2Seq 或 Transformer 小翻译/摘要玩具任务。 citeturn6search0turn6search3turn3search5turn5search11turn3search0

本节小结:经典网络结构之所以值得学,是因为它们把"训练稳定性、计算效率、任务输出结构"这些永恒主题都讲明白了。你只要把关键模块(归一化、残差、注意力、可分离/膨胀卷积)与两套训练模板真正跑熟,后续读任何新架构都会快很多。

相关推荐
人还是要有梦想的2 小时前
QT的基本学习路线
开发语言·qt·学习
源码之家2 小时前
计算机毕业设计:基于Python的美食数据采集可视化系统 Django框架 Scrapy爬虫 可视化 数据分析 大数据 机器学习 食物 食品(建议收藏)✅
python·算法·机器学习·信息可视化·课程设计
xx_xxxxx_2 小时前
常见多模态架构CLIP/BLIP/Llava/CogVLM
人工智能·深度学习·机器学习·transformer·多模态
VelinX2 小时前
【个人学习||算法】贪心算法
学习·算法·贪心算法
烤麻辣烫2 小时前
I/O流 进阶流
java·开发语言·学习·intellij-idea
源码之家2 小时前
计算机毕业设计:Python智慧交通大数据监控系统 Flask框架 可视化 百度地图 汽车 车况 数据分析 大模型 机器学习(建议收藏)✅
大数据·python·算法·机器学习·信息可视化·flask·课程设计
硅基流动2 小时前
硅基流动 × DeepStudent:内置 10+ 项技能,开源 AI 学习智能体
人工智能·学习
不灭锦鲤2 小时前
网络安全学习第162天
学习·安全·web安全
承渊政道2 小时前
【优选算法】(实战掌握分治思想的使用方法)
数据结构·c++·笔记·vscode·学习·算法·leetcode