这个例子直接摘自PyTorch文档。我对深度学习有一定的背景知识,知道forward
调用代表的是前向传递,数据通过不同的层,最终到达末端,在这种情况下有10个输出,然后你会使用定义好的损失函数来计算前向传递的输出loss
。现在,我忘了在这种情况下forward()
传递的具体输出是什么。
我以为神经网络的最后一层应该是某种激活函数,比如sigmoid()
或softmax()
,但我没有在任何地方看到这些函数的定义。此外,当我最近做项目时,我发现softmax()
是在后面被调用的。所以我想澄清一下outputs = net(inputs)
究竟给了我什么,根据这个链接,似乎PyTorch模型的前向传递的输出默认是logits?
transform = transforms.Compose( [transforms.ToTensor(), transforms.Normalize((0.5, 0.5, 0.5), (0.5, 0.5, 0.5))])trainset = torchvision.datasets.CIFAR10(root='./data', train=True, download=True, transform=transform)trainloader = torch.utils.data.DataLoader(trainset, batch_size=4, shuffle=True, num_workers=2)import torch.nn as nnimport torch.nn.functional as Fclass Net(nn.Module): def __init__(self): super(Net, self).__init__() self.conv1 = nn.Conv2d(3, 6, 5) self.pool = nn.MaxPool2d(2, 2) self.conv2 = nn.Conv2d(6, 16, 5) self.fc1 = nn.Linear(16 * 5 * 5, 120) self.fc2 = nn.Linear(120, 84) self.fc3 = nn.Linear(84, 10) def forward(self, x): x = self.pool(F.relu(self.conv1(x))) x = self.pool(F.relu(self.conv2(x))) x = x.view(-1, 16 * 5 * 5) x = F.relu(self.fc1(x)) x = F.relu(self.fc2(x)) x = self.fc3(x) return xnet = Net()import torch.optim as optimcriterion = nn.CrossEntropyLoss()optimizer = optim.SGD(net.parameters(), lr=0.001, momentum=0.9)for epoch in range(2): # loop over the dataset multiple times running_loss = 0.0 for i, data in enumerate(trainloader, 0): # get the inputs; data is a list of [inputs, labels] inputs, labels = data # zero the parameter gradients optimizer.zero_grad() # forward + backward + optimize outputs = net(inputs) print(outputs) break loss = criterion(outputs, labels) loss.backward() optimizer.step() # print statistics running_loss += loss.item() if i % 2000 == 1999: # print every 2000 mini-batches print('[%d, %5d] loss: %.3f' % (epoch + 1, i + 1, running_loss / 2000)) running_loss = 0.0print('Finished Training')
回答:
似乎PyTorch模型的前向传递的输出默认是logits
从前向传递中可以看出,是的,你的函数确实传递了原始输出
def forward(self, x): x = self.pool(F.relu(self.conv1(x))) x = self.pool(F.relu(self.conv2(x))) x = x.view(-1, 16 * 5 * 5) x = F.relu(self.fc1(x)) x = F.relu(self.fc2(x)) x = self.fc3(x) return x
那么,softmax在哪里呢?就在这里:
criterion = nn.CrossEntropyLoss()
这有点隐蔽,但在这个函数内部处理了softmax计算,当然,它使用的是你最后一层的原始输出
这是softmax的计算方式:
其中z_i是神经网络的原始输出
所以,总的来说,你的最后一个输入层没有激活函数,因为它由nn.CrossEntropyLoss
类处理
回答来自nn.Linear
的原始输出是什么:神经网络层的原始输出是来自前一层神经元的值的线性组合