简体   繁体   English

CNN 给出随机答案,而完全连接的神经网络工作正常

[英]CNN giving random answers while fully-connected neural network works fine

I'm working on an AI that should analyze images and recognize 5 possible objects.我正在研究一个应该分析图像并识别 5 个可能对象的 AI。 I am using tf.keras in python, which worked fine on a previous project, but for this one it gives random results (20% accuracy with 5 possible outputs), no matter how long I train it.我在 python 中使用 tf.keras,它在以前的项目中运行良好,但对于这个项目,无论我训练多长时间,它都会给出随机结果(20% 的准确度和 5 个可能的输出)。

The 5 possible objects are : - Four-legged animals - Humain figures - Airplanes - Trucks - Cars 5 种可能的对象是: - 四足动物 - 人类模型 - 飞机 - 卡车 - 汽车

I tried with a fully-connected neural network before, with the exact same data set, and it worked with a ~50% accuracy with 10 minutes of training.我之前尝试过使用完全连接的神经网络,使用完全相同的数据集,经过 10 分钟的训练,它的准确率约为 50%。 My goal is to reach 90% accuracy, that's why I'm trying to use a CNN instead.我的目标是达到 90% 的准确率,这就是我尝试使用 CNN 的原因。 I also played a bit with the mnist dataset and made a cnn that recognize hand-written digits, using tf.keras.我还使用了 mnist 数据集并制作了一个使用 tf.keras 识别手写数字的 cnn。 I tried to use the same keras model, but it failed.我尝试使用相同的 keras 模型,但失败了。 I tried different models, and all of them failed to give non-random predictions.我尝试了不同的模型,但都没有给出非随机预测。

Here is my keras model :这是我的 keras 模型:

import tensorflow as tf

layers = tf.keras.layers

model = tf.keras.models.Sequential([
    layers.Conv2D(16, (3, 3), input_shape=(80, 80, 1), activation='relu'),
    layers.MaxPooling2D(pool_size=(2, 2)),
    layers.Conv2D(32, (3, 3), activation='relu'),
    layers.MaxPooling2D(pool_size=(2, 2)),
    layers.Conv2D(64, (3, 3), activation='relu'),
    layers.MaxPooling2D(pool_size=(2, 2)),
    layers.Dropout(0.2),
    layers.Flatten(),
    layers.Dense(512, activation=tf.nn.relu),
    layers.Dense(5, activation=tf.nn.softmax)
])
model.compile(optimizer='adam',
              loss='sparse_categorical_crossentropy',
              metrics=['accuracy']
)

And I'm training it with this piece of code :我正在用这段代码训练它:

x, y = self.load_data(input("File containg train files: "), input("File containg labels files: ")) # function that takes a .mat file and return an array of shape (29160, 1, 80, 80)

x = x.reshape(total_data_number, 80, 80, 1)
x = x.astype('float32')
x /= 255.0

epoch = 15

model.fit(x, y, batch_size=50, epochs=epoch, verbose=1)

The fully-connected model was this one :全连接模型是这样的:

model = tf.keras.models.Sequential([
tf.keras.layers.Flatten(input_shape=(80, 80, 1)),
tf.keras.layers.Dense(512, activation=tf.nn.relu),
tf.keras.layers.Dropout(0.2),
tf.keras.layers.Dense(5, activation=tf.nn.softmax)
])
model.compile(optimizer='adam',
loss='sparse_categorical_crossentropy',
metrics=['accuracy'])

The accuracy should be way higher than 20%, and should improve when I train the model.准确率应该高于 20%,并且在我训练模型时应该会提高。

Some of your problem may come from the fact that you are using sparse_categorical_crossentropy whereas your output is a one_hot_encoded vector.您的一些问题可能来自这样一个事实,即您使用的是sparse_categorical_crossentropy而您的输出是 one_hot_encoded 向量。 So you should use categorical_crossentropy instead.所以你应该使用categorical_crossentropy代替。 (basic explanation here ) (基本解释在这里

How many data do you have for each classes?每个班级有多少数据? Beside, your model seems too simple for an object classification task.此外,您的模型对于对象分类任务来说似乎太简单了。 You should try deeper models.您应该尝试更深层次的模型。 Keras provides some pretrained models on imagenet . Keras 在imagenet上提供了一些预训练模型。 You may finetune those models on your own dataset.您可以在自己的数据集上微调这些模型。 For example on Keras Application it provides a way to finetune a pretrianed InceptionV3 model:例如,在Keras 应用程序上,它提供了一种微调预训练的 InceptionV3 模型的方法:

from keras.applications.inception_v3 import InceptionV3
from keras.preprocessing import image
from keras.models import Model
from keras.layers import Dense, GlobalAveragePooling2D
from keras import backend as K

# create the base pre-trained model
base_model = InceptionV3(weights='imagenet', include_top=False)

# add a global spatial average pooling layer
x = base_model.output
x = GlobalAveragePooling2D()(x)
# let's add a fully-connected layer
x = Dense(1024, activation='relu')(x)
# and a logistic layer -- 4 classes in your case
predictions = Dense(4, activation='softmax')(x)

# this is the model we will train
model = Model(inputs=base_model.input, outputs=predictions)

# first: train only the top layers (which were randomly initialized)
# i.e. freeze all convolutional InceptionV3 layers
for layer in base_model.layers:
    layer.trainable = False

# compile the model (should be done *after* setting layers to non-trainable)
model.compile(optimizer='rmsprop', loss='categorical_crossentropy')

# train the model on the new data for a few epochs
model.fit_generator(...)

# at this point, the top layers are well trained and we can start fine-tuning
# convolutional layers from inception V3. We will freeze the bottom N layers
# and train the remaining top layers.

# let's visualize layer names and layer indices to see how many layers
# we should freeze:
for i, layer in enumerate(base_model.layers):
   print(i, layer.name)

# we chose to train the top 2 inception blocks, i.e. we will freeze
# the first 249 layers and unfreeze the rest:
for layer in model.layers[:249]:
   layer.trainable = False
for layer in model.layers[249:]:
   layer.trainable = True

# we need to recompile the model for these modifications to take effect
# we use SGD with a low learning rate
from keras.optimizers import SGD
model.compile(optimizer=SGD(lr=0.0001, momentum=0.9), loss='categorical_crossentropy')

# we train our model again (this time fine-tuning the top 2 inception blocks
# alongside the top Dense layers
model.fit_generator(...)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 为什么即使输入的维数较大,keras神经网络中最后一个完全连接/密集的层也希望具有2个暗角? - Why does the last fully-connected/dense layer in a keras neural network expect to have 2 dim even if its input has more dimensions? ResNet(2D 图像)与全连接网络(1D 输入)的串联 - Concatenation of ResNet (2D images) with fully-connected network (1D input) 再现全连接顺序层 - Reproducing Fully-Connected Sequential Layer 我的神经网络完全连接内核初始化时出错 - Error on my neural network fully connected kernel initialisation 尝试为 CIFAR-10 创建一个完全连接的神经网络 - Trying to create a fully connected neural network for CIFAR-10 如何实现以非全连接层作为最后一层的神经网络? - How to implement a neural network with a not-fully-connected layer as the final layer? python 中全连接深度神经网络输入的重塑误差 - reshape error of fully connected deep neural network input in python 如何获得完全连接层中神经元的数量? - How to get the number of the neurons in the fully-connected layer? 卷积神经网络(CNN)python - Convolutional neural network(CNN) python 为什么重塑我的数据会完全改变 Keras 中全连接神经网络的行为? - Why does reshaping my data completely change the behaviour of a fully connected neural network in Keras?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM