训练时 RNN-LSTM 准确率没有提高

时间:2021-03-06 11:35:09

标签: python machine-learning keras lstm recurrent-neural-network

我正在尝试使用 keras RNN-LSTM 算法通过使用传感器数据(X/Y/Z 加速度计数据、X/Y/Z 陀螺仪数据、欧拉角等)对 9 种不同的坐姿进行分类。

训练数据是通过在 8 个测试对象的背部放置 3 个传感器,并让他们坐在 9 个不同的坐姿上来记录的。前 3 名测试对象在每个位置上坐了 2 分钟,最后一个 5 每个位置坐 3 分钟。

不同的测试对象记录了这些数据量(按行):

  • 主题 1:52824
  • 主题 2:51490
  • 主题 3:52019
  • 主题 4:80613
  • 主题 5:70143
  • 主题 6:79231
  • 主题 7:16027
  • 主题 8:15780

所有录音都记录为 CSV 文件,时间戳(每个 CSV 文件中的第一列)从 0,0000 开始直到试用期。

阶段之间的转换(测试对象改变坐姿)从数据集中剪掉,因此我们的时间序列中有一些小“洞”。

将所有这些行组合在一起,我们的 X_train 集包含 418127 行和 39 列。

np.shape(x_train) // (418127, 39)

而我的 y_train 集合是一个一维数组,其中包含与 x_train 集合中具有相同索引的行对应的正确标签。

np.shape(y_train) // (418127,)

由于 RNN-LSTM 模型需要一个 3d 数组作为输入,因此我创建了一种从 X-train 集创建 3d 数组的方法。


def create_3d_array(array, num_timestamps):

    arr_3d = []
    temp_2d = []
    for i in range(1,len(array)):
        temp_2d.append(array[0])
        if i % NUM_TIMESTAMPS == 0:
            arr_3d.append(temp_2d)
            temp_2d = []
    print("x_train: ", np.shape(arr_3d))
    
    return arr_3d

生成的 3d 数组的形状取决于序列(#timestamps)的长度。

问题 1:在这个特定示例中,作为 RNN-LSTM 模型输入的 3d 数组的拟合序列长度是多少?该模型是否应该具有长序列,或者 RNN-LSTM 模型在小序列上也能正常工作?

为了能够进行多类分类,我还对 y_train 进行了单热编码。

np.shape(x_train_3d) //(20906,20,39)
np.shape(y_train_3d) //(20906, 9)

我之前尝试过使用序列长度为 20(每个样本 20 个时间戳)和这个模型。 我想让它尽可能简单,因此将模型实现为 RNN-LSTM Vanilla。

model = Sequential()
model.add(layers.LSTM(2, activation='relu', input_shape=[x_train.shape[1], x_train.shape[2]]))
model.add(Dense(9, activation='softmax'))
model.compile(optimizer=OPTIM, loss=tf.keras.losses.CategoricalCrossentropy(), metrics=['accuracy'])
model.fit(x=x_train, batch_size=5, y=y_train, epochs=10, shuffle=False)



Epoch 1/10
4182/4182 [==============================] - 28s 7ms/step - loss: 4.9613 - accuracy: 0.7435
Epoch 2/10
4182/4182 [==============================] - 19s 5ms/step - loss: 4.7745 - accuracy: 0.7447
Epoch 3/10
4182/4182 [==============================] - 52s 12ms/step - loss: 4.7731 - accuracy: 0.7447
Epoch 4/10
4182/4182 [==============================] - 47s 11ms/step - loss: 4.7731 - accuracy: 0.7447
Epoch 5/10
4182/4182 [==============================] - 61s 15ms/step - loss: 4.7731 - accuracy: 0.7447
Epoch 6/10
4182/4182 [==============================] - 69s 16ms/step - loss: 4.7731 - accuracy: 0.7447
Epoch 7/10
4182/4182 [==============================] - 70s 17ms/step - loss: 4.7731 - accuracy: 0.7447
Epoch 8/10
4182/4182 [==============================] - 62s 15ms/step - loss: 4.7731 - accuracy: 0.7447
Epoch 9/10
4182/4182 [==============================] - 52s 12ms/step - loss: 4.7731 - accuracy: 0.7447
Epoch 10/10
4182/4182 [==============================] - 58s 14ms/step - loss: 4.7731 - accuracy: 0.7447

测试数据的生成方式相同,但样本较少,每个位置记录约 20 秒。

np.shape(x_test) // (8367, 39) 
np.shape(y_test) // (8367,)

同样的方法也用于测试数据,产生这些形状:


np.shape(x_test) //(418, 20, 39)
np.shape(y_test) //(418, 9)

模型评估:

model.evaluate(x_test,y_test, batch_size=5)

418/418 [==============================] - 2s 6ms/step - loss: 14.3449 - accuracy: 0.1172
[14.344941139221191, 0.11722487956285477]

问题 2:为什么准确率没有提高,为什么评估结果如此糟糕?

1 个答案:

答案 0 :(得分:0)

我试着给你一些建议,因为过去我也发现自己的模型没有改进。首先,如果您看到模型在训练级别保持静止,然后在测试级别它没有给出不错的结果,您必须立即考虑过度拟合。可能因为您使用了 Dense (9),我会尝试增加 LSTM 层的数量和大小,也许会添加另一个具有更多单元格的层。之后我看到你没有设置学习率,你为什么不试试预定的学习率呢?它给了我很好的结果。它还使用批次进行训练以避免过拟合。