我可以在 pytorch 中访问 DeepLab 的内层输出吗?

Posted

技术标签:

【中文标题】我可以在 pytorch 中访问 DeepLab 的内层输出吗?【英文标题】:Can I access the inner layer outputs of DeepLab in pytorch? 【发布时间】:2021-05-05 03:45:06 【问题描述】:

使用 Pytorch,我正在尝试实现一个使用预训练的 DeepLab ResNet-101 的网络。 我找到了两种可能的方法来使用这个网络:

this one

 torchvision.models.segmentation.deeplabv3_resnet101(
     pretrained=False, progress=True, num_classes=21, aux_loss=None, **kwargs)

但是,我可能不仅需要这个网络的输出,还需要几个内部层的输出。 有没有办法使用这些方法之一访问内层输出?

如果没有 - 是否可以手动复制经过训练的 resnet 的参数,以便我可以手动重新创建它并自己添加这些输出? (希望第一个选项是可能的,所以我不需要这样做)

谢谢!

【问题讨论】:

【参考方案1】:

您可以使用forward hooks 轻松实现此目的。

这个想法是遍历模型的模块,找到您感兴趣的层,​​将回调函数挂钩到它们。调用时,这些层将触发钩子。我们将利用这一点来保存中间输出。

例如,假设您要获取层 classifier.0.convs.3.1 的输出:

layers = ['classifier.0.convs.3.1']
activations = 

def forward_hook(name):
    def hook(module, x, y):
        activations[name] = y
    return hook

for name, module in model.named_modules():
    if name in layers:
        module.register_forward_hook(forward_hook(name))

*forward_hook 的作用域围绕hook() 进行的闭包用于包含您此时无法访问的模块名称。

一切准备就绪,我们可以调用模型了

>>> model = torchvision.models.segmentation.deeplabv3_resnet101(
        pretrained=True, progress=True, num_classes=21, aux_loss=None)

>>> model(torch.rand(16, 3, 100, 100))

正如预期的那样,在推断之后,activations 将有一个新条目 'classifier.0.convs.3.1' - 在这种情况下 - 将包含一个形状为 (16, 256, 13, 13) 的张量。


不久前,I wrote an answer 提出了一个类似的问题,其中更详细地介绍了如何使用钩子来检查中间输出形状。

【讨论】:

以上是关于我可以在 pytorch 中访问 DeepLab 的内层输出吗?的主要内容,如果未能解决你的问题,请参考以下文章

pytorch从零开始用语义分割网络(deeplab3+)训练自己的数据集

我可以将 deeplab 微调到 tensorflow 中的自定义数据集吗?

如何在 Xcode 中应用 Deeplab V3 进行实时分割?

caffe系列:deeplab中的插值网络层前传和反传的实现分析

获得 Deeplab 对小/欠平衡类的更严格的分割结果

在 Google Colab 上与在本地机器上训练 DeepLab ResNet V3 之间的巨大差异