Почему я всегда получаю то же значение, что и результат в CNN в pytorch?

#pytorch #classification #conv-neural-network

#pytorch #классификация #conv-нейронная сеть

Вопрос:

Вот мой код

 dataset = pd.read_csv('augmented_data.csv')
dataset = dataset.sample(frac=1)

class ConvNet(nn.Module):
def __init__(self):
    super(ConvNet, 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(1024144, 120)
    self.fc2 = nn.Linear(120, 84)
    self.fc3 = nn.Linear(84,1)

def forward(self, x):
    x = self.pool(F.relu(self.conv1(x)))
    x = self.pool(F.relu(self.conv2(x)))
    x = x.view(-1, 1024144)
    x = F.relu(self.fc1(x))
    x = F.relu(self.fc2(x))
    print(x)
    x = self.fc3(x)
    return x   

files_read = 0
preprocess = transforms.Compose([
transforms.Resize(1024),
transforms.ToTensor(),
transforms.Normalize((0.5, 0.5, 0.5),(0.5, 0.5, 0.5))])

# device = torch.device('cuda' if torch.cuda.is_available else 'cpu')
device = torch.device('cpu')

# model = ConvNet().to(device)

criterion = torch.nn.MSELoss(reduction='sum')
optimizer = optim.Adam(model.parameters(), lr=0.001)

results = []    
for index, row in dataset.iterrows():
    try:
      image = load_img('padded_images/'   row['image_name']  '.jpg')
    except:
      image = load_img('augmented_images/'   row['image_name']  '.jpeg')

    files_read  = 1

    input_tensor = preprocess(image)
    input_batch = input_tensor.unsqueeze(0).to(device)

    if files_read <= 80 * len(dataset) // 100:
        output = model(input_batch)
        optimizer.zero_grad()
    
        y = torch.tensor([[float(row['target'])]]).to(device)
        loss = criterion(output, y)
    
        loss.backward()
        optimizer.step()
    else:
        model.eval()
        output = model(input_batch)
        results.append([1.0 if output[0][0].double() > 0.5 else 0, float(row['target'])])

     
 

Итак, я использую pytorch CNN для классификации 60 тысяч изображений в 2 класса. Когда я печатаю выходные данные после обучения модели, каким бы ни было изображение в качестве входных данных, вывод всегда будет «тензор ([[0.6384]], grad_fn =)». Всегда одно и то же значение. Таким образом, он предсказывает только 1 (потому что он больше 0,5). Дело в том, что когда я печатаю вывод во время обучения, результаты меняются (16, 1 , 0, 4 ,0.6 и т.д.), но когда я печатаю выходные данные (с той же моделью, но не обученные), результаты не так сильно меняются (0.5, 0.51, 0.49 0.52, 0.55). Поэтому я думаю, можно с уверенностью сказать, что он сходится к одному значению. Я просто не знаю, почему. что я мог сделать по-другому?

Комментарии:

1. Для задачи двоичной классификации вы должны использовать BCE вместо MSE. Также с чем вы пытались сделать transforms.Normalize((0.5, 0.5, 0.5),(0.5, 0.5, 0.5))]) ?

2. я видел нормализацию, используемую в примерах обучения передаче, и я использовал ее. я изменю mse на bce, но все же я не понимаю, почему моя модель не может правильно оценить

3. у вас есть линейный слой размером 1024144 x 120 . Вы уверены в этом? вы понимаете, что это значит?

4. Да, мои изображения очень большие, поэтому мне нужно так много входных данных для этого слоя. Я думаю, что это правильно. Я не думаю, что проблема в этом

5. Ваш код показывает, что вы обучаете свою модель только для одной эпохи.. Так что он едва обучен, когда вы его оцениваете. Можете ли вы попробовать (много) больше эпох?