小白学Pytorch系列--Torch.nn API Vision Layers(15)

本文介绍了Pytorch中用于图像处理的几个关键模块,包括nn.PixelShuffle和nn.PixelUnshuffle,它们分别用于执行上采样的像素重排和下采样的反向操作。nn.Upsample则提供了一般性的上采样功能,支持最近邻和双线性插值方法。这些API在深度学习模型中常用于调整特征图的尺寸。
摘要由CSDN通过智能技术生成

小白学Pytorch系列–Torch.nn API Vision Layers(15)

方法注释
nn.PixelShuffle将形状张量 ( ∗ , C r 2 , H , W ) (*,C r^2,H,W) (Cr2,H,W)中的元素重新排列为形状张量 ( ∗ , C , H r , W r ) (*,C,H r,W r) (C,Hr,Wr),其中r是一个高阶因子。
nn.PixelUnshuffle通过将形状张量 ( ∗ , C , H r , W r ) (*,C,H r,W r) (C,Hr,Wr)中的元素重新排列为形状张量 ( ∗ , C r 2 , H , W ) (*,C r^2,H,W) (Cr2,H,W)来反转PixelShuffle操作,其中r是一个降尺度因子。
nn.Upsample对给定的多通道1D(时间)、2D(空间)或3D(体积)数据进行上采样。
nn.UpsamplingNearest2d对由多个输入通道组成的输入信号应用二维最近邻上采样。
nn.UpsamplingBilinear2d对由多个输入通道组成的输入信号应用二维双线性上采样。

nn.PixelShuffle

将形状张量 ( ∗ , C r 2 , H , W ) (*,C r^2,H,W) (Cr2,H,W)中的元素重新排列为形状张量 ( ∗ , C , H ∗ r , W ∗ r ) (*,C,H * r,W *r) (C,Hr,Wr),其中r是一个高阶因子。

>>> pixel_shuffle = nn.PixelShuffle(3)
>>> input = torch.randn(1, 9, 4, 4)
>>> output = pixel_shuffle(input)
>>> print(output.size())
torch.Size([1, 1, 12, 12])

nn.PixelUnshuffle

通过将形状张量 ( ∗ , C , H ∗ r , W ∗ r ) (*,C,H* r,W *r) (C,Hr,Wr)中的元素重新排列为形状张量 ( ∗ , C r 2 , H , W ) (*,C r^2,H,W) (Cr2,H,W)来反转PixelShuffle操作,其中r是一个降尺度因子。

>>> pixel_unshuffle = nn.PixelUnshuffle(3)
>>> input = torch.randn(1, 1, 12, 12)
>>> output = pixel_unshuffle(input)
>>> print(output.size())
torch.Size([1, 9, 4, 4])

nn.Upsample



>>> input = torch.arange(1, 5, dtype=torch.float32).view(1, 1, 2, 2)
>>> input
tensor([[[[1., 2.],
          [3., 4.]]]])

>>> m = nn.Upsample(scale_factor=2, mode='nearest')
>>> m(input)
tensor([[[[1., 1., 2., 2.],
          [1., 1., 2., 2.],
          [3., 3., 4., 4.],
          [3., 3., 4., 4.]]]])

>>> m = nn.Upsample(scale_factor=2, mode='bilinear')  # align_corners=False
>>> m(input)
tensor([[[[1.0000, 1.2500, 1.7500, 2.0000],
          [1.5000, 1.7500, 2.2500, 2.5000],
          [2.5000, 2.7500, 3.2500, 3.5000],
          [3.0000, 3.2500, 3.7500, 4.0000]]]])

>>> m = nn.Upsample(scale_factor=2, mode='bilinear', align_corners=True)
>>> m(input)
tensor([[[[1.0000, 1.3333, 1.6667, 2.0000],
          [1.6667, 2.0000, 2.3333, 2.6667],
          [2.3333, 2.6667, 3.0000, 3.3333],
          [3.0000, 3.3333, 3.6667, 4.0000]]]])

>>> # Try scaling the same data in a larger tensor
>>> input_3x3 = torch.zeros(3, 3).view(1, 1, 3, 3)
>>> input_3x3[:, :, :2, :2].copy_(input)
tensor([[[[1., 2.],
          [3., 4.]]]])
>>> input_3x3
tensor([[[[1., 2., 0.],
          [3., 4., 0.],
          [0., 0., 0.]]]])

>>> m = nn.Upsample(scale_factor=2, mode='bilinear')  # align_corners=False
>>> # Notice that values in top left corner are the same with the small input (except at boundary)
>>> m(input_3x3)
tensor([[[[1.0000, 1.2500, 1.7500, 1.5000, 0.5000, 0.0000],
          [1.5000, 1.7500, 2.2500, 1.8750, 0.6250, 0.0000],
          [2.5000, 2.7500, 3.2500, 2.6250, 0.8750, 0.0000],
          [2.2500, 2.4375, 2.8125, 2.2500, 0.7500, 0.0000],
          [0.7500, 0.8125, 0.9375, 0.7500, 0.2500, 0.0000],
          [0.0000, 0.0000, 0.0000, 0.0000, 0.0000, 0.0000]]]])

>>> m = nn.Upsample(scale_factor=2, mode='bilinear', align_corners=True)
>>> # Notice that values in top left corner are now changed
>>> m(input_3x3)
tensor([[[[1.0000, 1.4000, 1.8000, 1.6000, 0.8000, 0.0000],
          [1.8000, 2.2000, 2.6000, 2.2400, 1.1200, 0.0000],
          [2.6000, 3.0000, 3.4000, 2.8800, 1.4400, 0.0000],
          [2.4000, 2.7200, 3.0400, 2.5600, 1.2800, 0.0000],
          [1.2000, 1.3600, 1.5200, 1.2800, 0.6400, 0.0000],
          [0.0000, 0.0000, 0.0000, 0.0000, 0.0000, 0.0000]]]])

nn.UpsamplingNearest2d

>>> input = torch.arange(1, 5, dtype=torch.float32).view(1, 1, 2, 2)
>>> input
tensor([[[[1., 2.],
          [3., 4.]]]])

>>> m = nn.UpsamplingNearest2d(scale_factor=2)
>>> m(input)
tensor([[[[1., 1., 2., 2.],
          [1., 1., 2., 2.],
          [3., 3., 4., 4.],
          [3., 3., 4., 4.]]]])

nn.UpsamplingBilinear2d

>>> input = torch.arange(1, 5, dtype=torch.float32).view(1, 1, 2, 2)
>>> input
tensor([[[[1., 2.],
          [3., 4.]]]])

>>> m = nn.UpsamplingBilinear2d(scale_factor=2)
>>> m(input)
tensor([[[[1.0000, 1.3333, 1.6667, 2.0000],
          [1.6667, 2.0000, 2.3333, 2.6667],
          [2.3333, 2.6667, 3.0000, 3.3333],
          [3.0000, 3.3333, 3.6667, 4.0000]]]])
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
好的,关于Vision Transformer模型的搭建,我可以给你一些指导。 首先,你需要导入PyTorch和一些其他的必要库。下面是一个简单的示例: ```python import torch import torch.nn as nn import torch.nn.functional as F from einops.layers.torch import Rearrange ``` 接下来,你需要定义模型的各个模块。一个标准的Vision Transformer模型由多个Transformer层组成,每个Transformer层包含了多头自注意力机制、前馈网络和残差连接。下面是一个简单的Transformer层的示例: ```python class TransformerBlock(nn.Module): def __init__(self, embed_dim, num_heads, dropout=0.1): super().__init__() self.attention = nn.MultiheadAttention(embed_dim, num_heads) self.norm1 = nn.LayerNorm(embed_dim) self.dropout1 = nn.Dropout(dropout) self.fc = nn.Sequential( nn.Linear(embed_dim, 4 * embed_dim), nn.GELU(), nn.Linear(4 * embed_dim, embed_dim), nn.Dropout(dropout) ) self.norm2 = nn.LayerNorm(embed_dim) self.dropout2 = nn.Dropout(dropout) def forward(self, x): attn_output, _ = self.attention(x, x, x) x = self.norm1(x + self.dropout1(attn_output)) fc_output = self.fc(x) x = self.norm2(x + self.dropout2(fc_output)) return x ``` 接下来,你需要将多个Transformer层堆叠起来组成一个完整的Vision Transformer模型。这个示例中,我们还添加了一个可训练的分类头用于图像分类任务: ```python class VisionTransformer(nn.Module): def __init__(self, num_classes, image_size=224, patch_size=16, embed_dim=768, depth=12, num_heads=12, mlp_ratio=4., dropout=0.1): super().__init__() assert image_size % patch_size == 0, "Image size must be divisible by patch size." num_patches = (image_size // patch_size) ** 2 patch_dim = 3 * patch_size ** 2 self.patch_embedding = nn.Sequential( Rearrange('b c (h p1) (w p2) -> b (h w) (p1 p2 c)', p1=patch_size, p2=patch_size), nn.Linear(patch_dim, embed_dim), nn.Dropout(dropout) ) self.positional_encoding = nn.Parameter(torch.zeros(1, num_patches + 1, embed_dim)) self.cls_token = nn.Parameter(torch.zeros(1, 1, embed_dim)) self.transformer_blocks = nn.ModuleList([ TransformerBlock(embed_dim, num_heads, dropout) for _ in range(depth) ]) self.mlp_head = nn.Sequential( nn.LayerNorm(embed_dim), nn.Linear(embed_dim, int(embed_dim * mlp_ratio)), nn.GELU(), nn.Dropout(dropout), nn.Linear(int(embed_dim * mlp_ratio), num_classes) ) def forward(self, x): b = x.shape[0] x = self.patch_embedding(x) cls_tokens = self.cls_token.expand(b, -1, -1) x = torch.cat((cls_tokens, x), dim=1) x += self.positional_encoding[:, :(x.shape[1]), :] for transformer_block in self.transformer_blocks: x = transformer_block(x) x = x.mean(dim=1) x = self.mlp_head(x) return x ``` 最后,你可以实例化该模型并传递输入数据来进行推理或训练: ```python model = VisionTransformer(num_classes=10) input_data = torch.randn((1, 3, 224, 224)) output = model(input_data) ``` 希望这能够帮助到你。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

发呆的比目鱼

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值