Предобученная модель CNN делает плохие прогнозы на наборе тестовых изображений.

Вопрос или проблема

Я пробовал использовать несколько предобученных моделей (MobileNet) для мультиклассовых предсказаний. У нас 42 класса, и распределение изображений равномерное по всем 42 классам.

Вот мой код:

base_model=MobileNet(weights="imagenet",include_top=False,input_shape = (224,224,3)) #импортирует модель mobilenet и отбрасывает последний слой из 1000 нейронов.
x=base_model.output
x=GlobalAveragePooling2D()(x)
x=Dense(512,activation='relu')(x) #мы добавляем плотные слои, чтобы модель могла обучаться более сложным функциям и классифицировать для лучших результатов.
preds=Dense(42,activation='softmax')(x) #финальный слой с активацией softmax
model=Model(inputs=base_model.input,outputs=preds)
for layer in base_model.layers[:20]:
    layer.trainable=False
for layer in base_model.layers[20:]:
    layer.trainable=True

Я заморозил и разморозил некоторые из обучаемых слоев.

Я дал ему проработать 5 эпох:

Epoch 1/5
1318/1318 [==============================] - 3604s 3s/step - loss: 1.5493 - accuracy: 0.5796 - val_loss: 1.7180 - val_accuracy: 0.5361
Epoch 2/5
1318/1318 [==============================] - 3272s 2s/step - loss: 1.2174 - accuracy: 0.6641 - val_loss: 1.7562 - val_accuracy: 0.5372
Epoch 3/5
1318/1318 [==============================] - 3233s 2s/step - loss: 1.0853 - accuracy: 0.6981 - val_loss: 1.2993 - val_accuracy: 0.6498
Epoch 4/5
1318/1318 [==============================] - 3223s 2s/step - loss: 0.9918 - accuracy: 0.7224 - val_loss: 1.3455 - val_accuracy: 0.6382
Epoch 5/5
1318/1318 [==============================] - 3310s 3s/step - loss: 0.9153 - accuracy: 0.7413 - val_loss: 1.2375 - val_accuracy: 0.6660

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

Мне интересно, правильно ли я импортировал тестовые изображения и сделал предсказания? Вот код:

import cv2
pred_images = []
filename= []

for image_file in os.listdir('./test/test'): #Извлечение имени файла изображения из папки с классами
    filename.append(image_file)
    image = cv2.imread('./test/test'+r"https://datascience.stackexchange.com/"+image_file) #Чтение изображения (OpenCV)
    image = cv2.resize(image,(224,224)) #Изменение размера изображения, некоторые изображения имеют разный размер. (Изменение размера очень важно)
    pred_images.append(image)

category = []
for i in range(len(pred_images)):
    pred_image = np.array([pred_images[i]])
    pred = model.predict(pred_image)
    cat = np.argmax(pred, axis = 1)
    category.extend(cat)

У меня получается DataFrame, выглядящий так, с множеством из класса 38 и 20. Есть ли что-то не так?

final = pd.DataFrame(list(zip(filename, category)), columns = ['filename', 'category'])
final.head()
    filename                               category
0   c94de2fa9b06d67848f648e33a43475c.jpg    38
1   bbb7a2da148488bb878727556aa5914c.jpg    38
2   606256bdf3636d280bfdc3def33a57e7.jpg    38
3   7f741619b952876e7c7c419a0de1ed60.jpg    20
4   05c7592b31ceb8e14d4faa30fa21794c.jpg    20

Набор данных Kaggle действительно шумный, и очень сложно получить очень хороший результат с простыми моделями. Вам нужно сделать много предварительной обработки, увеличения данных и большую сеть для многих эпох, чтобы получить хороший результат.
Вещи, которые вы можете сделать:

  1. Перейдите в раздел блокнотов вашей конкуренции и посмотрите на предварительную обработку и увеличения, и примените их.
  2. Используйте какие-либо регуляризаторы, такие как dropout, mixup, cutmix и многие другие.

3. Обучите свою модель в течение большего количества эпох.

  1. Обучите более крупную модель.

Ответ или решение

Предобученная модель CNN плохо предсказывает на тестовом наборе изображений

Проблема, с которой вы столкнулись, является распространенной среди специалистов по машинному обучению и может иметь множество причин. Все аспекты вашего кода и процесса обучения предоставляют информацию, которая может быть полезна для диагностики проблемы. Рассмотрим основные факторы, которые могут влиять на качество предсказаний вашей модели.

1. Проверка данных

Загрузка и предобработка тестовых изображений:

Сначала стоит убедиться, что вы корректно загружаете тестовые изображения. В вашем коде есть потенциальная ошибка в пути к изображению. Использование r"https://datascience.stackexchange.com/" выглядит неправильно, так как это URL, а не путь к файлу. Попробуйте:

image = cv2.imread('./test/test/' + image_file)

Также важно проверить, правильно ли обрабатываются изображения. Проверьте, не возникает ли ошибок при чтении изображений. Вы можете добавить вывод размера и типа загруженных изображений, чтобы убедиться, что они имеют нужный формат.

Нормализация данных:

Модели CNN, такие как MobileNet, ожидают нормализованные входные данные (например, значения пикселей в диапазоне от 0 до 1 или стандартизированные). Убедитесь, что вы применяете соответствующую нормализацию:

image = image / 255.0  # Нормализация

2. Настройки обучения

Качество обучения:

Хотя ваша модель показывает «относительно хорошие» результаты на обучающем наборе данных, это может не означать хорошее обобщение на тестовом наборе. Проверьте, не страдает ли ваша модель от переобучения. Это можно сделать, исследуя графики потерь и точности на обучающем и валидационном наборах.

3. Регуляризация

Ваша модель может быть слишком простой для такой сложной задачи. Попробуйте использовать технику регуляризации, такую как Dropout:

x = Dropout(0.5)(x)  # Пример добавления Dropout слоя

Это может помочь модели лучше обобщать данные.

4. Увеличение данных

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

from keras.preprocessing.image import ImageDataGenerator

datagen = ImageDataGenerator(
    rotation_range=20,
    width_shift_range=0.2,
    height_shift_range=0.2,
    shear_range=0.2,
    zoom_range=0.2,
    horizontal_flip=True,
    fill_mode="nearest"
)

# Примените к обучающему набору
model.fit(datagen.flow(train_images, train_labels, batch_size=32), ...)

5. Увеличение времени обучения и изменение архитектуры модели

Долговременное обучение:

Увеличение времени обучения может дать модели больше шансов на изучение важных признаков в данных. Рассмотрите возможность увеличения числа эпох и изменения темпа обучения.

Использование более сложных моделей:

Если вышеописанные подходы не помогают, возможно стоит попробовать использование более сложных архитектур, адаптированных для решения задач мультимодальной классификации, например, DenseNet или EfficientNet.

6. Валидация результатов

Наконец, обязательно используйте кросс-валидацию, чтобы оценить производительность вашей модели более строго. Это поможет вам лучше понять, как ваша модель реагирует на различные подмножества данных.

Заключение

Используя эти рекомендации, вы сможете улучшить качество предсказаний вашей модели на тестовой выборке. Всегда учитывайте качество входящих данных, опыт на валидационных наборах и необходимость применения более сложных архитектур. Эти аспекты играют ключевую роль в обеспечении надежных и точных результатов в задачах классификации с использованием нейронных сетей.

Оцените материал
Добавить комментарий

Капча загружается...