Вопрос или проблема
Я работаю над задачей классификации. Мои входные данные – это метки, а ожидаемые выходные данные – это метки. Я создал пары X, Y, сдвинув X, и Y изменились на категориальное значение.
Метки Количество
1 94481
0 65181
2 60448
X Y
2 1.0
1 2.0
1 1.0
2 1.0
2 2.0
encoder = LabelEncoder()
test_labels = to_categorical(encoder.fit_transform(values[:,1]),num_classes=3)
train_X,test_X,train_y,test_y= train_test_split(values[:,0], test_labels,test_size = 0.30,random_state = 42)
print(train_X.shape)
print(train_y.shape)
print(test_X.shape)
print(test_y.shape)
(154076,)
(154076, 3)
(66033,)
(66033, 3)
Приведение этого к формату LSTM
train_X = train_X.reshape(train_X.shape[0],1,1)
test_X = test_X.reshape(test_X.shape[0],1,1)
# настройка сети
n_batch = 1
n_epoch = 10
n_neurons = 100
Архитектура модели
tf.keras.backend.clear_session()
model = tf.keras.models.Sequential([
tf.keras.layers.LSTM(n_neurons, batch_input_shape=(n_batch, train_X.shape[1],train_X.shape[2]), stateful=True),
tf.keras.layers.Dense(64, activation='relu'),
tf.keras.layers.Dense(100, activation = 'relu',kernel_regularizer=regularizers.l2(0.0001)),
tf.keras.layers.Dense(3, activation='softmax')
])
model.summary()
model.compile(optimizer="rmsprop",
loss="categorical_crossentropy",
metrics=['acc'])
history = model.fit(train_X,train_y,validation_data=(test_X, test_y),epochs=n_epoch, batch_size=n_batch, verbose=1,shuffle= False)
Точность валидации не меняется
Epoch 1/5
154076/154076 [==============================] - 356s 2ms/step - loss: 1.0844 - acc: 0.4269 - val_loss: 1.0814 - val_acc: 0.4310
Epoch 2/5
154076/154076 [==============================] - 354s 2ms/step - loss: 1.0853 - acc: 0.4256 - val_loss: 1.0813 - val_acc: 0.4310
Epoch 3/5
154076/154076 [==============================] - 355s 2ms/step - loss: 1.0861 - acc: 0.4246 - val_loss: 1.0814 - val_acc: 0.4310
Epoch 4/5
154076/154076 [==============================] - 356s 2ms/step - loss: 1.0874 - acc: 0.4228 - val_loss: 1.0825 - val_acc: 0.4310
Epoch 5/5
154076/154076 [==============================] - 353s 2ms/step - loss: 1.0887 - acc: 0.4208 - val_loss: 1.0828 - val_acc: 0.4310
Что можно изменить, чтобы улучшить модель?
Обновление 2
После увеличения скорости обучения Rmsprop до 0.5, ниже находятся значения потерь при обучении и валидации
Epoch 1/10
176087/176087 [==============================] - 370s 2ms/step - loss: 1.4314 - acc: 0.3594 - val_loss: 12.9380 - val_acc: 0.2739
Epoch 2/10
176087/176087 [==============================] - 369s 2ms/step - loss: 1.3209 - acc: 0.3593 - val_loss: 4.6767 - val_acc: 0.2854
Epoch 3/10
176087/176087 [==============================] - 371s 2ms/step - loss: 1.3209 - acc: 0.3592 - val_loss: 12.9380 - val_acc: 0.2739
Epoch 4/10
176087/176087 [==============================] - 370s 2ms/step - loss: 1.3209 - acc: 0.3592 - val_loss: 4.6767 - val_acc: 0.2854
Epoch 5/10
176087/176087 [==============================] - 368s 2ms/step - loss: 1.3209 - acc: 0.3593 - val_loss: 12.9380 - val_acc: 0.2739
Epoch 6/10
176087/176087 [==============================] - 370s 2ms/step - loss: 1.3209 - acc: 0.3593 - val_loss: 4.6767 - val_acc: 0.2854
Epoch 7/10
176087/176087 [==============================] - 368s 2ms/step - loss: 1.3209 - acc: 0.3593 - val_loss: 12.9380 - val_acc: 0.2739
Epoch 8/10
176087/176087 [==============================] - 372s 2ms/step - loss: 1.3209 - acc: 0.3593 - val_loss: 4.6767 - val_acc: 0.2854
Epoch 9/10
176087/176087 [==============================] - 371s 2ms/step - loss: 1.3209 - acc: 0.3593 - val_loss: 12.9379 - val_acc: 0.2739
Epoch 10/10
176087/176087 [==============================] - 369s 2ms/step - loss: 1.3209 - acc: 0.3593 - val_loss: 4.6767 - val_acc: 0.2854
Из документации:
входы: 3D тензор с формой [пакет, временные шаги, признаки].
Вы хотите сказать, что хотите 1 вход и 1 признак, но хотите выдать 100 нейронов? Я бы рассмотрел возможность добавления большего количества временных шагов.
train_X = train_X.reshape(train_X.shape[0],10,1)
test_X = test_X.reshape(test_X.shape[0],10,1)
Также я бы не добавлял регуляризацию к активации ReLU без пакетной нормализации. На самом деле, я, вероятно, использовал бы дропаут вместо регуляризации. Учитывайте, что при регуляризации многие нейроны ReLU могут “умереть”.
Ответ или решение
Почему валидационная точность LSTM-модели не изменяется?
Вы столкнулись с проблемой, когда валидационная точность вашей LSTM-модели не меняется на протяжении нескольких эпох обучения. Это может происходить по нескольким причинам. Ниже перечислены наиболее вероятные из них с предложениями по решениям.
1. Проблемы с подготовкой данных
-
Общие проблемы с данными: Убедитесь, что ваши входные данные (X) и выходные данные (Y) должным образом соответствуют друг другу и что данные сбалансированы. Чрезмерное число экземпляров одного класса по сравнению с другими может привести к тому, что модель будет обучаться на этом классе, игнорируя остальные.
-
Проблемы с форматом входных данных: Вы правильно преобразовали данные в трехмерный формат для LSTM (размерность
[кол-во образцов, временные шаги, признаки]
), но стоит использовать больше временных шагов, например,10
, вместо1
. Это позволит модели извлекать временные зависимости более эффективно:train_X = train_X.reshape(train_X.shape[0], 10, 1) test_X = test_X.reshape(test_X.shape[0], 10, 1)
2. Архитектура модели
-
Количество нейронов: Ваша архитектура модели может быть слишком простой или сложной для задачи, что может вести к переобучению или недообучению. Попробуйте добавить больше слоев LSTM или Dense или изменить количество нейронов.
-
Регуляризация и активация: У вас используется L2-регуляризация на слоях с ReLU-активацией, что может привести к "умиранию" нейронов. Лучше использовать дроп-аут, если вы хотите предотвратить переобучение:
model = tf.keras.models.Sequential([ tf.keras.layers.LSTM(n_neurons, return_sequences=True, input_shape=(timesteps, features)), tf.keras.layers.Dropout(0.5), tf.keras.layers.Dense(64, activation='relu'), tf.keras.layers.Dropout(0.5), tf.keras.layers.Dense(3, activation='softmax') ])
3. Гиперпараметры
- Скорость обучения: Вы увеличили скорость обучения до значения
0.5
, что, скорее всего, слишком высоко. Попробуйте снизить её до0.001
или0.01
, чтобы позволить модели более плавно обучаться и избежать резких колебаний в функции потерь:optimizer = tf.keras.optimizers.RMSprop(learning_rate=0.001)
4. Проверка эффекта обучаемости
-
Отслеживание изменений: Внимательно следите за изменениями функции потерь и точности как по обучающей, так и по валидационной выборкам. Если скорость обучения очень высока, модель может не видеть шаги, необходимые для обучения.
-
Визуализация: Используйте графики для визуализации обучения. Например, графики зависимости потерь и точности от эпох помогут вам выявить любое переобучение или недообучение.
5. Переобучение или недообучение
- Симптомы: Если функция потерь на обучающем наборе уменьшается, но не происходит улучшения на валидационном наборе, это указывает на переобучение. Если потери на обоих наборах высоки и не улучшаются, это может указывать на недообучение.
Заключение
Для решения проблемы с отсутствием изменений в валидационной точности вашей LSTM-модели, вам следует:
- Переосмыслить выбор архитектуры модели и добавить больше временных шагов.
- Снизить скорость обучения для лучшей сходимости.
- Рассмотреть замену регуляризации дроп-аутом и графическое отслеживание изменения метрик.
Работа с LSTM-моделями часто требует множества экспериментов с подготовкой данных и архитектурой. Не бойтесь пробовать новые подходы и анализировать результаты вашего обучения.