每一层均使用ReLU激活函数的PyTorch神经网络输出出现负值问题求助
问题核心原因
你对“每层都使用ReLU激活”的认知存在误区:前4层隐藏层确实配置了ReLU激活,经过这些层计算后输出的张量所有值都是非负的,但最后一层输出层linear5后面没有加任何激活函数。全连接层本身的计算逻辑是y = x @ W.T + b,只要对应输出维度的权重W或偏置b存在负值,即便输入的x全部为非负,也完全可以计算出负值,这和你观测到的单维度输出为负的现象完全吻合。
验证方案
- 你可以在forward函数中打印第四层ReLU输出后的张量,确认所有值均为非负,再打印
linear5对应异常输出维度的权重和偏置,即可直接定位是线性计算产生了负值。
解决方案
如果你需要保证所有输出均为非负,可根据你的数据特性选择以下方案:
- 输出层新增ReLU激活:直接截断所有负值,只要你的目标值本身都是非负的,该改动不会影响正常训练,反而会强制输出符合取值范围。
修改forward函数的输出部分代码如下:
out = self.linear5(out) out = nn.ReLU()(out) return out
更规范的写法是在__init__中定义self.relu_out = nn.ReLU(),forward部分直接调用即可。
2. 如果你的目标输出不仅非负,还存在0-1区间限制,可替换为Sigmoid激活;如果要求7个输出的和为1,可替换为Softmax激活,可根据你的化学数据实际特性选择。
3. 额外的代码优化建议:你当前在每个训练/验证步都重新实例化MSELoss,存在不必要的性能开销,可将损失函数定义在__init__中全局复用:
# __init__中新增 self.loss_fn = nn.MSELoss() # 训练、验证步骤中直接调用self.loss_fn(out, targets)即可
内容的提问来源于stack exchange,提问作者MMM
相关产品推荐
相关产品推荐

