我是Pytorch的新手,所以我尝试通过创建简单的猫狗分类来学习它。 代码:
class DogCatClassifier(nn.Module):
def __init__(self):
super().__init__()
self.conv1 = nn.Conv2d(1, 32, 5)
self.conv2 = nn.Conv2d(32, 64, 5)
self.conv3 = nn.Conv2d(64, 128, 5)
self.fc1 = nn.Linear(512, 256)
self.fc2 = nn.Linear(256, 2)
def forward(self, x):
x = F.max_pool2d(F.relu(self.conv1(x)), (2, 2))
print("1-st: ", x.shape)
x = F.max_pool2d(F.relu(self.conv2(x)), (2, 2))
print("2-nd: ", x.shape)
x = F.max_pool2d(F.relu(self.conv3(x)), (2, 2))
print("3-rd: ", x.shape)
x = torch.flatten(x, start_dim=1)
x = F.relu(self.fc1(x))
print("6-th: ", x.shape)
x = self.fc2(x) # bc this is our output layer. No activation here.
print("7-th: ", x.shape)
x = F.sigmoid(x)
print("8-th: ", x.shape)
return x
我传递了一批数据(数据形状为(50,1,50,50)
model = DogCatClassifier()
images, labels = next(iter(train_loader))
preds = model(images)
print(pred)
loss = F.binary_cross_entropy(preds, labels)
我的预测形状是(50,2),所以据我所知F.binary_cross_entropy(preds,标签)从单个图像检查两个预测,这就是为什么我对50个标签获得100个预测的原因。来自张量流,我认为我可以实现相同的逻辑,例如使用sigmoid作为最后一次激活,使用binary_cross_entropy作为损失函数。我不明白的是如何使这段代码起作用。
答案 0 :(得分:0)
出现问题是因为您使用的是二进制交叉熵而不是规则交叉熵。顾名思义,它会检查标签是否正确,因此两个张量(代码中的pred和标签)的形状应该相同。当您提供两个类的置信度时,BCE损失函数会感到困惑,并且代码崩溃。您可以做两件事:
1-更改为F.cross_entropy(preds,标签)作为损失函数。
2-更改代码以选择最大值作为目标。
text
让我知道这是否可行,如果无法解决,请更新为新错误。