1.deeplabv3是在deeplabv2的基础上修改ASSP模块。deeplabv1加上个ASSP就是deeplabv2。deeplabv1相关介绍看我的博文:https://blog.csdn.net/gbz3300255/article/details/105681119
2.ASSP模块介绍以及代码(deeplabv3):
先原理后代码。原理就是下面这张图。(这个图是deeplabv3+的图。我感觉ASSP部分特别清晰就直接拿来用了.... deeplabv3+与deeplabv3的区别就是在decoder部分做了工作)
上面的encoder部分就是一个ASPP的pytorch实现过程,图中的G I模块是deeplabv3+特有结构,前面的到F的模块就是deeplabv3的ASSP模块了。
class ASPP(nn.Module):
def __init__(self, num_classes):
super(ASPP, self).__init__()
self.conv_1x1_1 = nn.Conv2d(2048, 256, kernel_size=1)
self.bn_conv_1x1_1 = nn.BatchNorm2d(256)
#空洞卷积 小感受野
self.conv_3x3_1 = nn.Conv2d(2048, 256, kernel_size=3, stride=1, padding=6, dilation=6)
self.bn_conv_3x3_1 = nn.BatchNorm2d(256)
#空洞卷积 中感受野
self.conv_3x3_2 = nn.Conv2d(2048, 256, kernel_size=3, stride=1, padding=12, dilation=12)
self.bn_conv_3x3_2 = nn.BatchNorm2d(256)
#空洞卷积 大感受野
self.conv_3x3_3 = nn.Conv2d(2048, 256, kernel_size=3, stride=1, padding=18, dilation=18)
self.bn_conv_3x3_3 = nn.BatchNorm2d(256)
self.avg_pool = nn.AdaptiveAvgPool2d(1)
self.conv_1x1_2 = nn.Conv2d(2048, 256, kernel_size=1)
self.bn_conv_1x1_2 = nn.BatchNorm2d(256)
self.conv_1x1_3 = nn.Conv2d(1280, 256, kernel_size=1) # (1280 = 5*256)
self.bn_conv_1x1_3 = nn.BatchNorm2d(256)
self.conv_1x1_4 = nn.Conv2d(256, num_classes, kernel_size=1)
def forward(self, feature_map):
# (feature_map has shape (batch_size, 2048, h/8, w/8))
#输入的feature_map是经过主干网卷积后的结果,比如resnet xception等吧
feature_map_h = feature_map.size()[2] # (h/8)
feature_map_w = feature_map.size()[3] # (w/8)
out_1x1 = F.relu(self.bn_conv_1x1_1(self.conv_1x1_1(feature_map))) # (shape: (batch_size, 256, h/8, w/8)) 对应图中 E
out_3x3_1 = F.relu(self.bn_conv_3x3_1(self.conv_3x3_1(feature_map))) # (shape: (batch_size, 256, h/8, w/8)) 对应图中 D
out_3x3_2 = F.relu(self.bn_conv_3