在深度学习的CV(计算机视觉)和NLP(自然语言处理)任务中,理解张量形状在不同网络层中的变化至关重要。以下是常见网络层及其输入/输出形状变化的细致总结(使用PyTorch/Numpy的维度约定:(Batch Size, Channels/Features/Embedding Dim, Height, Width)(Batch Size, Sequence Length, Hidden Size/Embedding Dim)):


核心维度概念

1.N / batch_size: 批次大小(样本数)
2.C / channels / features / embedding_dim / d_model / hidden_size: 特征维度(通道、词嵌入大小、隐藏层大小)
3.H: 特征图高度 (CV)
4.W: 特征图宽度 (CV)
5.L / seq_len: 序列长度 (NLP / 1D CV)
6.K: 卷积核大小 (单个维度)
7.S / stride: 步长
8.P / padding: 填充 (通常指单边添加的数量)
9.D / dilation: 膨胀率
10. O / out_channels: 卷积输出通道数
11. G / groups: 分组数 (分组卷积)
12. num_heads: Transformer中的注意力头数


常见层及其形状变化

1. 全连接层 (Linear / Dense / Feed-Forward)

*输入形状: (N, *, In_Features)
** 表示任意数量的额外维度(会被展平)。
*In_Features 是输入特征维度。
*输出形状: (N, *, Out_Features)
*变化说明:
*无论输入有多少额外维度(如序列长度L、图像高度H、宽度W),该层将所有额外维度 展平 (view(N, -1))。
*执行 Y = XW^T + b,其中 W 的形状是 (Out_Features, In_Features)

2. 卷积层 (Convolution)

*输入形状 (CV - 2D): (N, C_in, H_in, W_in)
*输出形状 (CV - 2D): (N, C_out, H_out, W_out)
*计算单个维度输出长度公式:
Output_Length = floor((Input_Length + 2 * Padding - Dilation * (Kernel_Size - 1) - 1) / Stride + 1)
*常见简化公式 (当 dilation=1):
Output_Length = floor((Input_Length + 2 * Padding - Kernel_Size) / Stride) + 1
*变化说明:
*通道数由 C_in 变为 C_out(由 out_channels 参数指定)。
*空间维度 (H, W) 根据上述公式收缩(通常)。
*分组卷积 (groups>1): 要求 C_inC_out 都能被 groups 整除。每个分组处理 C_in/groups 个输入通道,产生 C_out/groups 个输出通道,最后拼接。参数量显著减少。
*膨胀卷积 (dilation>1): 通过跳过输入像素扩大感受野,不影响通道数,但影响空间尺寸计算。
*输入形状 (NLP/1D - Conv1d): (N, C_in, L_in) (或有时定义为 (N, L_in, C_in),需注意框架约定)
*输出形状 (NLP/1D - Conv1d): (N, C_out, L_out)

3. 转置卷积层 (Transposed Convolution / Deconvolution / ConvTranspose)

*目的: 常用于上采样(如分割、生成模型)。
*输入形状 (CV - 2D): (N, C_in, H_in, W_in)
*输出形状 (CV - 2D): (N, C_out, H_out, W_out)
*计算单个维度输出长度公式:
Output_Length = (Input_Length - 1) * Stride - 2 * Padding + Dilation * (Kernel_Size - 1) + Output_Padding + 1
*简化公式 (常用参数 dilation=1, output_padding=0):
Output_Length = (Input_Length - 1) * Stride - 2 * Padding + Kernel_Size
*变化说明:
*通道数由 C_in 变为 C_out(由 out_channels 参数指定)。
*空间维度 (H, W) 根据上述公式 扩张(通常)。output_padding 用于解决因 stride>1 导致的形状模糊问题。

4. 池化层 (Pooling - Max, Avg, Adaptive)

*输入形状 (CV - 2D): (N, C, H_in, W_in)
*输出形状 (CV - 2D): (N, C, H_out, W_out)
*计算单个维度输出长度公式 (与卷积公式相同):
Output_Length = floor((Input_Length + 2 * Padding - Dilation * (Kernel_Size - 1) - 1) / Stride + 1)
Output_Length = floor((Input_Length + 2 * Padding - Kernel_Size) / Stride) + 1 (当 dilation=1)
*变化说明:
*通道数 C 保持不变(核心区别)。
*空间维度 (H, W) 根据上述公式收缩(通常)。
*自适应池化 (AdaptivePooling): 直接指定输出尺寸 (H_out, W_out),忽略 kernel_size, stride, padding。内部自动计算所需参数以达到目标尺寸。

5. 归一化层 (Normalization)

*批归一化 (BatchNorm - CV):
*输入形状: (N, C, H, W)
*输出形状: (N, C, H, W) (完全相同)
*变化说明: 沿 N, H, W 维度计算统计量 (均值、方差),对每个通道 C 独立进行缩放和平移。
*层归一化 (LayerNorm - NLP/CV):
*输入形状: (N, *, Normalized_Shape) (PyTorch)。Normalized_Shape 是最后几个需要归一化的维度(如 (L, C)(C,))。
*输出形状: (N, *, Normalized_Shape) (完全相同)
*变化说明: 沿指定的 Normalized_Shape 维度计算统计量(独立于 N 和其他未指定维度)。NLP 中常用 (..., L, C) 的最后两个维度 (L, C) 进行归一化(对每个样本的每个时间步的特征独立归一化)。
*实例归一化 (InstanceNorm - CV Style Transfer):
*输入形状: (N, C, H, W)
*输出形状: (N, C, H, W) (完全相同)
*变化说明: 沿 H, W 维度计算统计量,对每个样本 N 的每个通道 C 独立进行缩放和平移。

6. 循环神经网络层 (RNN, LSTM, GRU)

*输入形状: (N, L, H_in)(L, N, H_in) (PyTorch 通过 batch_first=True 控制,前者更常见)。
*输出形状:
***output:** (N, L, D * H_out)
*H_out 是隐藏层大小 (hidden_size)。
*D = 2 如果是双向RNN (bidirectional=True),否则 D = 1
hidden / (h_n, c_n) (LSTM):*
*h_n: (D * num_layers, N, H_out)
*c_n: (D * num_layers, N, H_out) (仅LSTM)
变化说明:*
*output 包含
所有时间步**的隐藏状态。
*hidden / (h_n, c_n) 包含
最后一个时间步**的隐藏状态(和细胞状态)。
*num_layers 决定了堆叠层数。
*输入维度 H_in 是输入特征大小,输出维度 H_out 是RNN单元定义的隐藏状态大小。

7. 嵌入层 (Embedding)

*输入形状: (N, L)(L, N) (包含整数索引)。
*输出形状: (N, L, E)(L, N, E)E 是嵌入维度 (embedding_dim)。
*变化说明: 将每个整数索引映射到一个 E 维的稠密向量。增加了特征维 E

8. Transformer 核心层

*输入形状: (N, L, d_model) (词嵌入序列 + 位置编码)。
*多头自注意力 (Multi-Head Self-Attention):
*输入: Q, K, V: 均为 (N, L, d_model)
*线性投影 (Q/K/V): (N, L, d_model) -> (N, L, num_heads * d_k) (通常 d_k = d_v = d_model / num_heads)
*Reshape: (N, L, num_heads * d_k) -> (N, L, num_heads, d_k) -> (N, num_heads, L, d_k) (转置以并行计算头)。
*计算注意力分数 & 输出: (N, num_heads, L, d_k) @ (N, num_heads, d_k, L) -> (N, num_heads, L, L) (分数)
*Softmax & Weighted Sum: (N, num_heads, L, L) @ (N, num_heads, L, d_v) -> (N, num_heads, L, d_v)
*Reshape & 拼接: (N, num_heads, L, d_v) -> (N, L, num_heads * d_v) = (N, L, d_model) (因为 d_v = d_model / num_heads)。
*线性投影 (输出): (N, L, d_model) -> (N, L, d_model) (可选,但标准Transformer有)。
*输出形状: (N, L, d_model) (与输入形状相同)。
*前馈网络 (Position-wise Feed-Forward Network - FFN):
*输入: (N, L, d_model)
*第一层: (N, L, d_model) -> (N, L, d_ff) (扩张,d_ff 通常 > d_model, 如 4*d_model)。
*激活函数 (如ReLU, GELU)。
*第二层: (N, L, d_ff) -> (N, L, d_model) (投影回 d_model)。
*输出形状: (N, L, d_model) (与输入形状相同)。
*层归一化 (LayerNorm) & 残差连接 (Add): 不改变形状 ((N, L, d_model) -> (N, L, d_model))。


关键总结与提示

1.N (Batch Size): 几乎总是贯穿所有层保持不变。
2.通道/特征维度 (C, H_in/H_out, embedding_dim, hidden_size, d_model):
*全连接层、卷积层 (out_channels)、嵌入层 (embedding_dim)、RNN (hidden_size)、Transformer (d_model) 显式改变此维度。
*池化层、归一化层(BatchNorm/InstanceNorm/LayerNorm)通常保持此维度不变(LayerNorm作用于指定的维度)。
3.空间/序列维度 (H, W, L):
*卷积层、池化层:根据公式改变尺寸(通常缩小)。
*转置卷积层:根据公式改变尺寸(通常扩大)。
*全连接层:展平(消失)。
*RNN、Transformer、嵌入层、归一化层 (LayerNorm作用于序列):保持序列长度 L 不变。
4.RNN/Transformer vs CNN:
*RNN/Transformer:核心处理维度是**序列长度 L + 特征维度 (hidden_size/d_model)**。
*CNN (CV):核心处理维度是**空间维度 (H, W) + 通道维度 C**。
5.框架约定: 特别注意维度顺序!PyTorch CV默认 (N, C, H, W),NLP默认 (L, N, *) 但常设 batch_first=True(N, L, *)。TensorFlow有时用 (N, H, W, C)
6.形状推导工具: 善用 model.summary() (Keras/TF), print(model) / torchinfo.summary() (PyTorch) 或直接 print(x.shape) 在模型中调试。
7.维度匹配: 形状错误最常见的原因是层之间维度不匹配(尤其是卷积/转置卷积输出尺寸计算错误,或全连接层输入未正确展平)。
8.自适应层: 当需要固定输出尺寸时(如分类头前),自适应池化 (AdaptiveAvgPool2d(1)) 非常有用,直接输出 (N, C, 1, 1) -> 展平为 (N, C)

理解这些核心层的形状变换规律是设计和调试深度学习模型的基础。务必结合具体公式和实际调试进行验证。