pytorch 我如何在nn.Sequential中添加整形层?

x8goxv8g  于 2022-11-09  发布在  其他
关注(0)|答案(1)|浏览(162)

因此,我正在实现GAN的生成器,我需要如下所示的架构:

问题是,当我尝试在BatchNorm和ReLU之后重新调整线性层的输出时(在图中为Dense,因为它们使用了Tensorflow),它会抛出错误:TypeError:reshape():参数'input'(位置1)必须是Tensor,而不是int

我知道这个错误,但是我找不到它的解决方法。有没有其他方法可以在nn.Sequential中重新整形,而不是显式调用torch?

class Generator(nn.Module):

    def __init__(self, z_dim=100, im_chan=1, hidden_dim=64, rdim=9216):

        super(Generator, self).__init__()
        self.z_dim = z_dim
        self.gen = nn.Sequential(
             nn.Linear(z_dim, rdim),
             nn.BatchNorm2d(rdim,momentum=0.9),
             nn.ReLU(inplace=True),
 ---->       torch.reshape(rdim, (6,6,256)), 
             self.make_gen_block(rdim, hidden_dim*2),
             self.make_gen_block(hidden_dim*2,hidden_dim),
             self.make_gen_block(hidden_dim,im_chan,final_layer=True),
        )
   def make_gen_block(self, input_channels, output_channels, kernel_size=1, stride=2, final_layer=False):

        if not final_layer:
           return nn.Sequential(
              nn.ConvTranspose2d(input_channels, output_channels, kernel_size, stride),
              nn.BatchNorm2d(output_channels),
              nn.ReLU(inplace=True)
        )
        else:
              return nn.Sequential(
              nn.ConvTranspose2d(input_channels, output_channels, kernel_size, stride),
              nn.Tanh()
        )

   def unsqueeze_noise(self, noise):
       return noise.view(len(noise), self.zdim, 1, 1)

   def forward(self, noise):
       x = self.unsqueeze_noise(noise)
       return self.gen(x)

def get_noise(n_samples, z_dim, device='cpu'):
    return torch.randn(n_samples, z_dim, device=device)

# Testing the Gen arch

gen = Generator()
num_test = 100

# test the hidden block

test_hidden_noise = get_noise(num_test, gen.z_dim)
test_hidden_block = gen.make_gen_block(6, 6, kernel_size=1,stride=2)
test_uns_noise = gen.unsqueeze_noise(test_hidden_noise)
hidden_output = test_hidden_block(test_uns_noise)
wwtsj6pe

wwtsj6pe1#

1.在nn.Sequential中,torch.nn.Unflatten()可以帮助你实现整形操作。
1.对于nn.Linear,其输入形状为(N, *, H_{in}),输出形状为(H, *, H_{out})。请注意,特征尺寸是最后一个。因此,unsqueeze_noise()在这里没有用。
1.根据网络结构,传递给make_gen_block的参数错误。
我已经检查了以下代码:

import torch
from torch import nn
class Generator(nn.Module):

   def __init__(self, z_dim=100, im_chan=1, hidden_dim=64, rdim=9216):

        super(Generator, self).__init__()
        self.z_dim = z_dim
        self.gen = nn.Sequential(
             nn.Linear(z_dim, rdim),
             nn.BatchNorm1d(rdim,momentum=0.9), # use BN1d
             nn.ReLU(inplace=True),
             nn.Unflatten(1, (256,6,6)), 
             self.make_gen_block(256, hidden_dim*2,kernel_size=2), # note arguments
             self.make_gen_block(hidden_dim*2,hidden_dim,kernel_size=2), # note kernel_size
             self.make_gen_block(hidden_dim,im_chan,kernel_size=2,final_layer=True), # note kernel_size
        )
   def make_gen_block(self, input_channels, output_channels, kernel_size=1, stride=2, final_layer=False):

        if not final_layer:
           return nn.Sequential(
              nn.ConvTranspose2d(input_channels, output_channels, kernel_size, stride),
              nn.BatchNorm2d(output_channels),
              nn.ReLU(inplace=True)
        )
        else:
              return nn.Sequential(
              nn.ConvTranspose2d(input_channels, output_channels, kernel_size, stride),
              nn.Tanh()
        )

   def forward(self, x):
       return self.gen(x)

def get_noise(n_samples, z_dim, device='cpu'):
    return torch.randn(n_samples, z_dim, device=device)

gen = Generator()
num_test = 100
input_noise = get_noise(num_test, gen.z_dim)
output = gen(input_noise)
assert output.shape == (num_test, 1, 48, 48)

相关问题