예제 #1
0
    def test_forward_output(self):
        device = torch.device("cuda")
        N, C, H, W = shape = 1, 1, 5, 5
        kernel_size = 3
        padding = 1

        inputs = torch.arange(np.prod(shape),
                              dtype=torch.float32).reshape(*shape).to(device)
        """
        0  1  2   3 4
        5  6  7   8 9
        10 11 12 13 14
        15 16 17 18 19
        20 21 22 23 24
        """
        offset_channels = kernel_size * kernel_size * 2
        offset = torch.full((N, offset_channels, H, W),
                            0.5,
                            dtype=torch.float32).to(device)

        # Test DCN v1
        deform = DeformConv(C, C, kernel_size=kernel_size,
                            padding=padding).to(device)
        deform.weight = torch.nn.Parameter(torch.ones_like(deform.weight))
        output = deform(inputs, offset)
        output = output.detach().cpu().numpy()
        deform_results = np.array([
            [30, 41.25, 48.75, 45, 28.75],
            [62.25, 81, 90, 80.25, 50.25],
            [99.75, 126, 135, 117.75, 72.75],
            [105, 131.25, 138.75, 120, 73.75],
            [71.75, 89.25, 93.75, 80.75, 49.5],
        ])
        self.assertTrue(np.allclose(output.flatten(),
                                    deform_results.flatten()))

        # Test DCN v2
        mask_channels = kernel_size * kernel_size
        mask = torch.full((N, mask_channels, H, W), 0.5,
                          dtype=torch.float32).to(device)
        modulate_deform = ModulatedDeformConv(C,
                                              C,
                                              kernel_size,
                                              padding=padding,
                                              bias=False).to(device)
        modulate_deform.weight = deform.weight
        output = modulate_deform(inputs, offset, mask)
        output = output.detach().cpu().numpy()
        self.assertTrue(
            np.allclose(output.flatten(),
                        deform_results.flatten() * 0.5))
예제 #2
0
 def __init__(self, chi, cho, norm='BN'):
     super(_DeformConv, self).__init__()
     self.actf = nn.Sequential(get_norm(norm, cho), nn.ReLU(inplace=True))
     if DCNV1:
         self.offset = Conv2d(chi,
                              18,
                              kernel_size=3,
                              stride=1,
                              padding=1,
                              dilation=1)
         self.conv = DeformConv(chi,
                                cho,
                                kernel_size=(3, 3),
                                stride=1,
                                padding=1,
                                dilation=1,
                                deformable_groups=1)
     else:
         self.offset = Conv2d(chi,
                              27,
                              kernel_size=3,
                              stride=1,
                              padding=1,
                              dilation=1)
         self.conv = ModulatedDeformConv(chi,
                                         cho,
                                         kernel_size=3,
                                         stride=1,
                                         padding=1,
                                         dilation=1,
                                         deformable_groups=1)
     nn.init.constant_(self.offset.weight, 0)
     nn.init.constant_(self.offset.bias, 0)
예제 #3
0
    def test_raise_exception(self):
        device = torch.device("cuda")
        N, C, H, W = shape = 1, 1, 3, 3
        kernel_size = 3
        padding = 1

        inputs = torch.rand(shape, dtype=torch.float32).to(device)
        offset_channels = kernel_size * kernel_size  # This is wrong channels for offset
        offset = torch.randn((N, offset_channels, H, W),
                             dtype=torch.float32).to(device)
        deform = DeformConv(C, C, kernel_size=kernel_size,
                            padding=padding).to(device)
        self.assertRaises(RuntimeError, deform, inputs, offset)

        offset_channels = kernel_size * kernel_size * 2
        offset = torch.randn((N, offset_channels, H, W),
                             dtype=torch.float32).to(device)
        mask_channels = kernel_size * kernel_size * 2  # This is wrong channels for mask
        mask = torch.ones((N, mask_channels, H, W),
                          dtype=torch.float32).to(device)
        modulate_deform = ModulatedDeformConv(C,
                                              C,
                                              kernel_size,
                                              padding=padding,
                                              bias=False).to(device)
        self.assertRaises(RuntimeError, modulate_deform, inputs, offset, mask)
예제 #4
0
    def test_small_input(self):
        device = torch.device("cuda")
        for kernel_size in [3, 5]:
            padding = kernel_size // 2
            N, C, H, W = shape = (1, 1, kernel_size - 1, kernel_size - 1)

            inputs = torch.rand(shape).to(
                device)  # input size is smaller than kernel size

            offset_channels = kernel_size * kernel_size * 2
            offset = torch.randn((N, offset_channels, H, W),
                                 dtype=torch.float32).to(device)
            deform = DeformConv(C, C, kernel_size=kernel_size,
                                padding=padding).to(device)
            output = deform(inputs, offset)
            self.assertTrue(output.shape == inputs.shape)

            mask_channels = kernel_size * kernel_size
            mask = torch.ones((N, mask_channels, H, W),
                              dtype=torch.float32).to(device)
            modulate_deform = ModulatedDeformConv(C,
                                                  C,
                                                  kernel_size,
                                                  padding=padding,
                                                  bias=False).to(device)
            output = modulate_deform(inputs, offset, mask)
            self.assertTrue(output.shape == inputs.shape)
    def __init__(self,
                 in_channels,
                 out_channels,
                 kernel_size=3,
                 stride=1,
                 padding=1,
                 dilation=1,
                 deformable_groups=1):
        super(DCN, self).__init__()

        channels_ = deformable_groups * 3 * kernel_size * kernel_size  # only support square kernels
        self.conv_offset_mask = nn.Conv2d(in_channels,
                                          channels_,
                                          kernel_size=kernel_size,
                                          stride=stride,
                                          padding=padding,
                                          bias=True)
        self.deform_conv = ModulatedDeformConv(
            in_channels,
            out_channels,
            kernel_size,
            stride,
            padding,
            dilation,
            deformable_groups=deformable_groups)
        self.init_offset()
예제 #6
0
 def __init__(
     self,
     in_channels,
     out_channels,
     kernel_size=3,
     stride=1,
     padding=1,
     dilation=1,
     groups=1,
     deformable_groups=1,
     norm=None,
     activation=None,
 ):
     super(ModulatedDeformConvWithOffset, self).__init__()
     self.dcn = ModulatedDeformConv(
         in_channels,
         out_channels,
         kernel_size,
         stride,
         padding,
         dilation,
         groups,
         deformable_groups,
         norm=norm,
         activation=activation,
     )
     self.mask = Conv2d(
         in_channels,
         deformable_groups * 3 * kernel_size * kernel_size,
         kernel_size=kernel_size,
         stride=stride,
         padding=padding,
     )
예제 #7
0
 def __init__(self, in_chs, out_chs, kernel_size=3, deformable_groups=1, activation='relu'):
     super(ModulatedDeformLayer, self).__init__()
     assert isinstance(kernel_size, (int, list, tuple))
     self.deform_offset = conv3x3(in_chs, (3 * kernel_size ** 2) * deformable_groups)
     self.act = actFunc(activation)
     self.deform = ModulatedDeformConv(
         in_chs,
         out_chs,
         kernel_size,
         stride=1,
         padding=1,
         deformable_groups=deformable_groups
     )
예제 #8
0
    def test_repr(self):
        module = DeformConv(3, 10, kernel_size=3, padding=1, deformable_groups=2)
        correct_string = (
            "DeformConv(in_channels=3, out_channels=10, kernel_size=(3, 3), "
            "stride=(1, 1), padding=(1, 1), dilation=(1, 1), "
            "groups=1, deformable_groups=2, bias=False)"
        )
        self.assertEqual(repr(module), correct_string)

        module = ModulatedDeformConv(3, 10, kernel_size=3, padding=1, deformable_groups=2)
        correct_string = (
            "ModulatedDeformConv(in_channels=3, out_channels=10, kernel_size=(3, 3), "
            "stride=1, padding=1, dilation=1, groups=1, deformable_groups=2, bias=True)"
        )
        self.assertEqual(repr(module), correct_string)