在Keras的MNIST数字识别中获得不同的测试数据准确性

时间:2018-11-08 13:01:08

标签: python machine-learning keras classification mnist

我正在使用Keras进行手写数字识别,我有两个文件: predict.py train.py

train.py 训练模型(如果尚未训练)并将其保存到目录中,否则只会从其保存到的目录中加载训练后的模型并打印{ {1}}和Test Loss

Test Accuracy

这里是输出(假设模型是较早训练的,这次将只加载模型):

  

('测试损失',1.741784990310669)

     

(“测试准确度”,0.414)

另一方面,

predict.py 会预测一个手写数字:

def getData():
    (X_train, y_train), (X_test, y_test) = mnist.load_data()
    y_train = to_categorical(y_train, num_classes=10)
    y_test = to_categorical(y_test, num_classes=10)
    X_train = X_train.reshape(X_train.shape[0], 784)
    X_test = X_test.reshape(X_test.shape[0], 784)

    # normalizing the data to help with the training
    X_train /= 255
    X_test /= 255


    return X_train, y_train, X_test, y_test

def trainModel(X_train, y_train, X_test, y_test):
    # training parameters
    batch_size = 1
    epochs = 10
    # create model and add layers
    model = Sequential()    
    model.add(Dense(64, activation='relu', input_shape=(784,)))
    model.add(Dense(10, activation = 'softmax'))


    # compiling the sequential model
    model.compile(loss='categorical_crossentropy', metrics=['accuracy'], optimizer='adam')
    # training the model and saving metrics in history
    history = model.fit(X_train, y_train,
          batch_size=batch_size, epochs=epochs,
          verbose=2,
          validation_data=(X_test, y_test))

    loss_and_metrics = model.evaluate(X_test, y_test, verbose=2)
    print("Test Loss", loss_and_metrics[0])
    print("Test Accuracy", loss_and_metrics[1])

    # Save model structure and weights
    model_json = model.to_json()
    with open('model.json', 'w') as json_file:
        json_file.write(model_json)
    model.save_weights('mnist_model.h5')
    return model

def loadModel():
    json_file = open('model.json', 'r')
    model_json = json_file.read()
    json_file.close()
    model = model_from_json(model_json)
    model.load_weights("mnist_model.h5")
    return model

X_train, y_train, X_test, y_test = getData()

if(not os.path.exists('mnist_model.h5')):
    model = trainModel(X_train, y_train, X_test, y_test)
    print('trained model')
    print(model.summary())
else:
    model = loadModel()
    print('loaded model')
    print(model.summary())
    model.compile(loss='categorical_crossentropy', optimizer='adam', metrics=['accuracy'])
    loss_and_metrics = model.evaluate(X_test, y_test, verbose=2)
    print("Test Loss", loss_and_metrics[0])
    print("Test Accuracy", loss_and_metrics[1])

在这种情况下,令我惊讶的是,得到了以下结果:

  

(“测试损失”,1.8380377866744995)

     

(“测试准确度”,0.8856)

在第二个文件中,我得到的def loadModel(): json_file = open('model.json', 'r') model_json = json_file.read() json_file.close() model = model_from_json(model_json) model.load_weights("mnist_model.h5") return model model = loadModel() model.compile(loss='categorical_crossentropy', optimizer='adam', metrics=['accuracy']) print(model.summary()) (X_train, y_train), (X_test, y_test) = mnist.load_data() y_test = to_categorical(y_test, num_classes=10) X_test = X_test.reshape(X_test.shape[0], 28*28) loss_and_metrics = model.evaluate(X_test, y_test, verbose=2) print("Test Loss", loss_and_metrics[0]) print("Test Accuracy", loss_and_metrics[1]) 为0.88(是我以前获得的两倍以上)。

此外,两个文件中的Test Accuracy都相同:

model.summery()

我无法弄清楚这种现象背后的原因。正常吗还是我错过了什么?

1 个答案:

答案 0 :(得分:0)

差异的原因是,您一次用规范化数据(即除以255)调用evaluate()方法,而另一次(即在“ predict.py”文件中)则用un调用它。 -标准化数据。在推断时间(即测试时间)中,您应始终使用与训练数据相同的预处理步骤。

此外,首先将数据转换为浮点数,然后将其除以255(否则,使用/,在Python 2.x和Python 3.x中会进行真正的除法,运行时会出错) X_train /= 255X_test /= 255):

X_train = X_train.astype('float32')
X_test = X_test.astype('float32')

X_train /= 255.
X_test /= 255.