我的Pytorch模型给出了非常糟糕的结果



我是Pytorch深度学习的新手。我对Tensorflow更有经验,因此我应该说我对深度学习本身并不陌生。

目前,我正在研究一个简单的ANN分类。只有两个类,所以我很自然地使用Softmax BCELoss组合。

数据集是这样的:

shape of X_train (891, 7)
Shape of Y_train (891,)
Shape of x_test (418, 7)

我将X_train和其他转换为火炬张量作为train_data等等。下一步是:

train_ds = TensorDataset(train_data, train_label)
# Define data loader
batch_size = 32
train_dl = DataLoader(train_ds, batch_size, shuffle=True)

我创建的模型类如下:

class Net(nn.Module):
def __init__(self):
super(Net, self).__init__()

# an affine operation: y = Wx + b
self.fc1 = nn.Linear(7, 32)
self.bc1 = nn.BatchNorm1d(32)
self.fc2 = nn.Linear(32, 64)
self.bc2 = nn.BatchNorm1d(64)
self.fc3 = nn.Linear(64, 128)
self.bc3 = nn.BatchNorm1d(128)
self.fc4 = nn.Linear(128, 32)
self.bc4 = nn.BatchNorm1d(32)
self.fc5 = nn.Linear(32, 10)
self.bc5 = nn.BatchNorm1d(10)
self.fc6 = nn.Linear(10, 1)
self.bc6 = nn.BatchNorm1d(1)

self.drop = nn.Dropout2d(p=0.5)


def forward(self, x):
torch.nn.init.xavier_uniform(self.fc1.weight)
x = self.fc1(x)
x = self.bc1(x)
x = F.relu(x)

x = self.drop(x)
x = self.fc2(x)
x = self.bc2(x)
x = F.relu(x)

#x = self.drop(x)
x = self.fc3(x)
x = self.bc3(x)
x = F.relu(x)

x = self.drop(x)
x = self.fc4(x)
x = self.bc4(x)
x = F.relu(x)

#x = self.drop(x)
x = self.fc5(x)
x = self.bc5(x)
x = F.relu(x)

x = self.drop(x)
x = self.fc6(x)
x = self.bc6(x)        
x = torch.sigmoid(x)
return x

model = Net()

定义了损失函数和优化器:

loss = nn.BCELoss()
optimizer = torch.optim.Adam(model.parameters(), lr=0.00001, betas=(0.9, 0.999), eps=1e-08, weight_decay=0, amsgrad=False)

最后,任务是按时代运行前进:

num_epochs = 1000
# Repeat for given number of epochs
for epoch in range(num_epochs):

# Train with batches of data
for xb,yb in train_dl:
pred = model(xb)

yb = torch.unsqueeze(yb, 1)

#print(pred, yb)
print('grad', model.fc1.weight.grad)

l = loss(pred, yb)
#print('loss',l)

# 3. Compute gradients
l.backward()

# 4. Update parameters using gradients
optimizer.step()

# 5. Reset the gradients to zero
optimizer.zero_grad()

# Print the progress
if (epoch+1) % 10 == 0:
print('Epoch [{}/{}], Loss: {:.4f}'.format(epoch+1, num_epochs, l.item()))

我可以在输出中看到,在所有批次的每次迭代之后,在应用了这个zero_grad之后,硬权重是非零的。

然而,模型是相当糟糕的。我的F1分数只有50%左右!当我调用它来预测train_dl本身时,模型是糟糕的!!

我想知道原因是什么。权重的梯度不为零,但没有正确更新?优化器没有优化权重?或者还有什么?谁能看一下吗?

我已经尝试了不同的损失函数和优化器。我尝试了更小的数据集,更大的批量,不同的超参数。

谢谢!:)

首先,您不使用softmax激活BCE损失,除非您有2个输出节点,这不是情况。在PyTorch中,BCE损失在计算损失之前不应用任何激活函数,不像CCE有内置的softmax函数。所以,如果你想使用BCE,你必须使用sigmoid(或任何函数f: R ->[0, 1])在输出层,而你没有。

此外,如果您希望执行SGD(这是默认值),理想情况下应该为每个批处理执行optimizer.zero_grad()。如果你不这样做,你将只是在做全批梯度下降,这是相当缓慢的,很容易陷入局部最小值。

最新更新