为什么我的损失趋于下降,而我的准确度却趋于零?
Why is my loss trending down while my accuracy is going to zero?
我正在尝试使用 Tensorflow/Keras 练习我的机器学习技能,但我在拟合模型时遇到了问题。让我解释一下我做了什么以及我在哪里。
我正在使用来自 Kaggle 的 Costa Rican Household Poverty Level Prediction Challenge
的数据集
因为我只是想熟悉 Tensorflow 工作流程,所以我通过删除一些有很多缺失数据的列来清理数据集,然后用它们的平均值填充其他列。所以我的数据集中没有缺失值。
接下来我使用 make_csv_dataset
从 TF 中加载新的、清理过的 csv。
batch_size = 32
train_dataset = tf.data.experimental.make_csv_dataset(
'clean_train.csv',
batch_size,
column_names=column_names,
label_name=label_name,
num_epochs=1)
我为 return 我的编译模型设置了一个函数,如下所示:
f1_macro = tfa.metrics.F1Score(num_classes=4, average='macro')
def get_compiled_model():
model = tf.keras.Sequential([
tf.keras.layers.Dense(512, activation=tf.nn.relu, input_shape=(137,)), # input shape required
tf.keras.layers.Dense(256, activation=tf.nn.relu),
tf.keras.layers.Dense(4, activation=tf.nn.softmax)
])
model.compile(optimizer='adam',
loss='binary_crossentropy',
metrics=[f1_macro, 'accuracy'])
return model
model = get_compiled_model()
model.fit(train_dataset, epochs=15)
下面是结果
A link 到我的笔记本是 Here
我应该提一下,我的实现很大程度上基于 Tensorflow 的鸢尾花数据 walkthrough
谢谢!
过了一会儿,我找到了您代码中的问题,它们按重要性排序。 (第一个最重要)
您正在进行多重class class化(不是二进制class化)。因此你的损失应该是categorical_crossentropy
.
你不是一个人在编码你的标签。使用 binary_crossentropy
并将标签作为数字 ID 绝对不是前进的方向。相反,您应该对标签进行单热编码,并像解决多 class class 化问题一样解决这个问题。以下是您的操作方法。
def pack_features_vector(features, labels):
"""Pack the features into a single array."""
features = tf.stack(list(features.values()), axis=1)
return features, tf.one_hot(tf.cast(labels-1, tf.int32), depth=4)
- 规范化您的数据。如果你看看你的训练数据。它们没有标准化。他们的价值观无处不在。因此,您应该考虑通过执行以下操作来规范化数据。这仅用于演示目的。您应该在 scikit learn 中阅读有关 Scalers 的内容,然后选择最适合您的内容。
x = train_df[feature_names].values #returns a numpy array
min_max_scaler = preprocessing.StandardScaler()
x_scaled = min_max_scaler.fit_transform(x)
train_df = pd.DataFrame(x_scaled)
这些问题应该让你的模型变直。
我正在尝试使用 Tensorflow/Keras 练习我的机器学习技能,但我在拟合模型时遇到了问题。让我解释一下我做了什么以及我在哪里。
我正在使用来自 Kaggle 的 Costa Rican Household Poverty Level Prediction Challenge
的数据集因为我只是想熟悉 Tensorflow 工作流程,所以我通过删除一些有很多缺失数据的列来清理数据集,然后用它们的平均值填充其他列。所以我的数据集中没有缺失值。
接下来我使用 make_csv_dataset
从 TF 中加载新的、清理过的 csv。
batch_size = 32
train_dataset = tf.data.experimental.make_csv_dataset(
'clean_train.csv',
batch_size,
column_names=column_names,
label_name=label_name,
num_epochs=1)
我为 return 我的编译模型设置了一个函数,如下所示:
f1_macro = tfa.metrics.F1Score(num_classes=4, average='macro')
def get_compiled_model():
model = tf.keras.Sequential([
tf.keras.layers.Dense(512, activation=tf.nn.relu, input_shape=(137,)), # input shape required
tf.keras.layers.Dense(256, activation=tf.nn.relu),
tf.keras.layers.Dense(4, activation=tf.nn.softmax)
])
model.compile(optimizer='adam',
loss='binary_crossentropy',
metrics=[f1_macro, 'accuracy'])
return model
model = get_compiled_model()
model.fit(train_dataset, epochs=15)
下面是结果
A link 到我的笔记本是 Here
我应该提一下,我的实现很大程度上基于 Tensorflow 的鸢尾花数据 walkthrough
谢谢!
过了一会儿,我找到了您代码中的问题,它们按重要性排序。 (第一个最重要)
您正在进行多重class class化(不是二进制class化)。因此你的损失应该是
categorical_crossentropy
.你不是一个人在编码你的标签。使用
binary_crossentropy
并将标签作为数字 ID 绝对不是前进的方向。相反,您应该对标签进行单热编码,并像解决多 class class 化问题一样解决这个问题。以下是您的操作方法。
def pack_features_vector(features, labels):
"""Pack the features into a single array."""
features = tf.stack(list(features.values()), axis=1)
return features, tf.one_hot(tf.cast(labels-1, tf.int32), depth=4)
- 规范化您的数据。如果你看看你的训练数据。它们没有标准化。他们的价值观无处不在。因此,您应该考虑通过执行以下操作来规范化数据。这仅用于演示目的。您应该在 scikit learn 中阅读有关 Scalers 的内容,然后选择最适合您的内容。
x = train_df[feature_names].values #returns a numpy array
min_max_scaler = preprocessing.StandardScaler()
x_scaled = min_max_scaler.fit_transform(x)
train_df = pd.DataFrame(x_scaled)
这些问题应该让你的模型变直。