如何在pytorch中实现Conv2d的棋盘大步?

安尼

我正在尝试使用pytorch创建一个convnet来处理2d矩阵的输入。我正在使用3x5滤镜,但我希望它具有如下的自定义步幅-在偶数行号上,我希望滤镜从位置0(图像中的红色)的元素开始,在奇数行号上,我希望它开始在位置1的元素上(图像中为蓝色),并且在两种情况下在x方向上的步幅均为2。这意味着,如果我有一个图像中的矩阵作为输入,我希望过滤器的中心只有0。我知道在卷积网络中这是非常不寻常的,但这实际上是物理学中的问题,因此准确的跨度很重要。输入上的3x5滤镜

乔达格

下面的自定义conv2d层按照原始问题中的指示在棋盘格跨度中实现卷积。这里的困难在于,pytorch并不真正支持这样的不一致步幅。也就是说,我们可以将该操作分为两个独立的跨步卷积,一个用于偶数行,一个用于奇数行。之后,我们可以将结果交织在一起。下面的代码中有一些细节,可确保我们正确填充(如果需要)。而且,该层完全支持反向传播。

import torch.nn as nn
import torch.nn.functional as F

class AMNI_Conv2d(nn.Module):
    def __init__(self, in_channels, out_channels, kernel_size, padding=0, bias=True):
        super().__init__()
        self.conv = nn.Conv2d(in_channels, out_channels, kernel_size, bias=bias, padding=padding)
        self.crow = self.conv.kernel_size[0] // 2
        self.ccol = self.conv.kernel_size[1] // 2

        # this module only works with odd sized kernels
        assert self.conv.kernel_size[0] % 2 == 1 and self.conv.kernel_size[1] % 2 == 1

    def forward(self, x):
        # currently only padding with zeros is supported
        if self.conv.padding[0] != 0 or self.conv.padding[1] != 0:
            x = F.pad(x, pad=(self.conv.padding[1], self.conv.padding[1], self.conv.padding[0], self.conv.padding[0]))

        # center filters on the "zeros" according to the diagram by AMNI, starting column for even/odd rows may need to change depending on padding/kernel size
        if (self.crow + self.ccol + self.conv.padding[0] + self.conv.padding[1]) % 2 == 0:
            x_even = F.conv2d(x[:, :, :-1, 1:], self.conv.weight, self.conv.bias, stride=2)
            x_odd = F.conv2d(x[:, :, 1:, :-1], self.conv.weight, self.conv.bias, stride=2)
        else:
            x_even = F.conv2d(x[:, :, :-1, :-1], self.conv.weight, self.conv.bias, stride=2)
            x_odd = F.conv2d(x[:, :, 1:, 1:], self.conv.weight, self.conv.bias, stride=2)
        b, c, h, w = x_even.shape

        # interleave even and odd rows back together
        return torch.stack((x_even, x_odd), dim=3).contiguous().view(b, c, -1, w)

该层基本上像普通的Conv2d一样起作用,但具有棋盘格跨度。

>>> x = torch.arange(64).view(1, 1, 8, 8).float()
tensor([[[[ 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., 25., 26., 27., 28., 29., 30., 31.],
          [32., 33., 34., 35., 36., 37., 38., 39.],
          [40., 41., 42., 43., 44., 45., 46., 47.],
          [48., 49., 50., 51., 52., 53., 54., 55.],
          [56., 57., 58., 59., 60., 61., 62., 63.]]]])

>>> layer = AMNI_Conv2d(1, 1, (3, 5), bias=False)

# set kernels to delta functions to demonstrate kernel centers
>>> with torch.no_grad():
...     layer.conv.weight.zero_()
...     layer.conv.weight[:,:,1,2] = 1

>>> result = layer(x)
tensor([[[[10., 12.],
          [19., 21.],
          [26., 28.],
          [35., 37.],
          [42., 44.],
          [51., 53.]]]], grad_fn=<ViewBackward>)

您也可以使用填充执行此操作,以使原始图中的每个“零”

>>> layer = AMNI_Conv2d(1, 1, (3, 5), padding=(1, 2), bias=False)

# set kernels to delta functions to demonstrate kernel centers
>>> with torch.no_grad():
...     layer.conv.weight.zero_()
...     layer.conv.weight[:,:,1,2] = 1

>>> result = layer(x)
tensor([[[[ 1.,  3.,  5.,  7.],
          [ 8., 10., 12., 14.],
          [17., 19., 21., 23.],
          [24., 26., 28., 30.],
          [33., 35., 37., 39.],
          [40., 42., 44., 46.],
          [49., 51., 53., 55.],
          [56., 58., 60., 62.]]]], grad_fn=<ViewBackward>)

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章

来自分类Dev

在PyTorch中如何实现Conv2d的算法

来自分类Dev

pytorch conv2d配重

来自分类Dev

我们如何在PyTorch中将线性层的输出提供给Conv2D?

来自分类Dev

如何在Tensor Flow 2.0中的Conv2D图层中指定输入形状

来自分类Dev

如何在keras中将Conv1D的输出与Conv2D的输出合并

来自分类Dev

自定义conv2d操作Pytorch

来自分类Dev

pytorch conv2d的源代码在哪里?

来自分类Dev

如何在多个图像输入中使用Conv2D?

来自分类Dev

如何在特定大小的conv2d层中使用Padding

来自分类Dev

Conv2D keras中的稳压器

来自分类Dev

在TensorFlow中编写类似Conv2D的操作

来自分类Dev

tensorflow中conv2d的顺序输出是什么?

来自分类Dev

在 Tensorflow 中查找 conv2d 层的权重

来自分类Dev

何时在Conv2d()中使用填充以及何时进行ReflectionPad2d()Pytorch

来自分类Dev

PyTorch Conv2D返回零输入张量的非零输出?

来自分类Dev

PyTorch conv2d不传播torch.channels_last内存格式

来自分类Dev

Keras:过度拟合的Conv2D

来自分类Dev

针对列表运行conv2d

来自分类Dev

如何使用张量流/ keras中的预定内核列表初始化Conv2D层?

来自分类Dev

角膜或张量流中的Conv2D层之后的ConvLSTM2D

来自分类Dev

如何在numpy中实现两层Keras conv1d?

来自分类Dev

Keras:转置Conv2D层的内核以在另一个Conv2D层中重用

来自分类Dev

如何理解Keras Conv2D层的第一个论点?

来自分类Dev

了解Keras Conv2D层中的参数数量

来自分类Dev

在Keras中是否可以看到Conv2D层之后的输出

来自分类Dev

在 Keras 的序列模型中添加 Conv2D 时出现属性错误

来自分类Dev

在Pytorch中实现SeparableConv2D

来自分类Dev

输入形状为 [?,1,1,5], [1,6,5,5] 的 'conv1d_2/convolution/Conv2D'(操作:'Conv2D')从 1 中减去 6 导致的负尺寸大小

来自分类Dev

如何在c中制作棋盘图案?

Related 相关文章

  1. 1

    在PyTorch中如何实现Conv2d的算法

  2. 2

    pytorch conv2d配重

  3. 3

    我们如何在PyTorch中将线性层的输出提供给Conv2D?

  4. 4

    如何在Tensor Flow 2.0中的Conv2D图层中指定输入形状

  5. 5

    如何在keras中将Conv1D的输出与Conv2D的输出合并

  6. 6

    自定义conv2d操作Pytorch

  7. 7

    pytorch conv2d的源代码在哪里?

  8. 8

    如何在多个图像输入中使用Conv2D?

  9. 9

    如何在特定大小的conv2d层中使用Padding

  10. 10

    Conv2D keras中的稳压器

  11. 11

    在TensorFlow中编写类似Conv2D的操作

  12. 12

    tensorflow中conv2d的顺序输出是什么?

  13. 13

    在 Tensorflow 中查找 conv2d 层的权重

  14. 14

    何时在Conv2d()中使用填充以及何时进行ReflectionPad2d()Pytorch

  15. 15

    PyTorch Conv2D返回零输入张量的非零输出?

  16. 16

    PyTorch conv2d不传播torch.channels_last内存格式

  17. 17

    Keras:过度拟合的Conv2D

  18. 18

    针对列表运行conv2d

  19. 19

    如何使用张量流/ keras中的预定内核列表初始化Conv2D层?

  20. 20

    角膜或张量流中的Conv2D层之后的ConvLSTM2D

  21. 21

    如何在numpy中实现两层Keras conv1d?

  22. 22

    Keras:转置Conv2D层的内核以在另一个Conv2D层中重用

  23. 23

    如何理解Keras Conv2D层的第一个论点?

  24. 24

    了解Keras Conv2D层中的参数数量

  25. 25

    在Keras中是否可以看到Conv2D层之后的输出

  26. 26

    在 Keras 的序列模型中添加 Conv2D 时出现属性错误

  27. 27

    在Pytorch中实现SeparableConv2D

  28. 28

    输入形状为 [?,1,1,5], [1,6,5,5] 的 'conv1d_2/convolution/Conv2D'(操作:'Conv2D')从 1 中减去 6 导致的负尺寸大小

  29. 29

    如何在c中制作棋盘图案?

热门标签

归档