Keras 模型(tensorflow 后端)在 python 3.5 中训练得非常好,但在 python 2.7 中非常糟糕

Posted

技术标签:

【中文标题】Keras 模型(tensorflow 后端)在 python 3.5 中训练得非常好,但在 python 2.7 中非常糟糕【英文标题】:Keras model (tensorflow backend) trains perfectly well in python 3.5 but very bad in python 2.7 【发布时间】:2018-11-25 03:00:11 【问题描述】:

我想做什么 我正在尝试在 Python 2.7 中使用 Keras 和 Tensorflow-GPU 作为后端来训练卷积神经网络 (CNN) 进行图像检测,因为我需要将它与仅支持 Python 2.7(而不是 3.5)的 ROS 动力学一起使用。我的模型是顺序的(代码见下文)。

我正在使用什么 Pycharm-社区 2018.1.4 Keras 2.2.0 TensorFlow-GPU 1.8.0 60000 张输入图像,100x100 像素(3 个通道),3 个类别(“train_set”) 20000 个评估图像,相同尺寸(“evaluation_set”)

什么有效 当使用 Python 3.5 在我的 train_set 上训练模型并使用 Python 3.5 对其进行评估时,它工作得非常好(train_accuracy:0.99874,evaluation_accuracy:0.9993)。

什么不起作用 当使用 Python 2.7 在我的 train_set 上训练模型并使用 Python 2.7 对其进行评估时,我的准确度急剧下降(train_accuracy:0.695,evaluation_accuracy:0.543),这只不过是猜测 3 个类(这将为 0.3333)。 我还尝试在 Python 3.5 中训练模型并在 Python 2.7 中加载它以进行评估和预测,但结果和以前一样差。

在所有情况下,我都使用完全相同的代码:

def build_model(training_input):
    model = Sequential()  
    model.add(Conv2D(32, (3, 3)) # Add some layers

    model.compile(optimizer='RMSprop', loss='categorical_crossentropy', metrics=['accuracy'])

def train():
    input_training = np.array(input_training_list)    # input_training_list is a list containing the imagedata
    labels_training = np.array(label_training_list)    # label_training_list is a list containing the labels corresponding to the imagedata
    model = create_model(input_training)
    history = model.fit(input_training, labels_training, epochs=10, shuffle=True, batch_size=20)
    model.save(model_directory + "my_model.h5")

def evaluation():
    input_evaluation = np.array(input_evaluation_list)
    labels_evaluation = np.array(label_evaluation_list)
    model = load_model(model_directory + "my_model.h5")
    loss, acc = model.evaluate(input_evaluation, labels_evaluation, batch_size=1)

我听说很多人使用不同的计算机或不同版本的 Python 在不同的 Sessions() 中加载相同的模型时遇到问题。但是在这里,相同的架构在两个 Python 版本中给出了完全不同的结果。

【问题讨论】:

如果你只是 model.save_weights() 然后在 Python 2 中重建模型并只是 model.load_weights() 会发生什么? @nuric 我刚刚在我的工作 Python 3.5 脚本中尝试了 model.save_weights("my_weights.h5"),在 Python 2.7 中构建了相同的模型/架构并将权重加载到该模型中 model.load_weights("my_weights.h5") 。但结果不会改变。让我感到困惑的是,即使在 Python 2.7 中训练模型也会产生如此糟糕的结果。 我会在两个平台上将软件包更新到最新版本,然后重试。 @nuric 两个平台上的所有包都是最新的,我只是重试了一切,没有任何变化。 可能是数据——你是如何得到它的,你有没有检查过它对于两个版本是否一致? 【参考方案1】:

我找到了我的问题的解决方案(感谢 user1735003 关于我的数据的提示)。 我的糟糕结果的原因是由于 Python 2.x 和 Python 3.x差异而导致的错误数据实现。在实现我的图像数据时,我使用

for i in range(len(evaluation_files)):
    input_evaluation = np.divide(ndimage.imread(evaluation_files[i]), 255)

但问题是:在 Python 3.x 中,这非常好用,因为两个整数相除会产生浮点数,但在 Python 2.x 中,结果也是整数,所以我的 input_evalution 列表只包含的零。我需要除以 255.0(使结果为浮点数)。

input_evaluation = np.divide(ndimage.imread(evaluation_files[i]), 255.0)

或者从__future__ 导入division 以从python 2 中已有的整数除法中获取浮点结果。

from __future__ import division

在使用 Python 2.x 或 Python 3.x 时存在一些主要差异,您可以在 http://sebastianraschka.com/Articles/2014_python_2_3_key_diff.html 上很好地看到这些差异。

我还管理在 Python 3.5 上训练我的模型,使用 model.save('my_model') 保存它并使用 keras.models.load_model('my_model') 将其加载到 Python 2.7 中,效果非常好。

也可以使用model.save_weights('my_weights') 轻松保存权重,在 Python 2.7 中创建相同架构的新模型(!)并使用 model.load_weights('my_weights') 将权重加载到该模型中,但由于仅加载模型本身就可以工作完全没问题,这样就容易多了。

【讨论】:

以上是关于Keras 模型(tensorflow 后端)在 python 3.5 中训练得非常好,但在 python 2.7 中非常糟糕的主要内容,如果未能解决你的问题,请参考以下文章

TensorFlow/Keras 多线程模型拟合

model.compile() 是不是初始化 Keras(tensorflow 后端)中的所有权重和偏差?

训练准确性增加,然后偶尔突然下降。使固定? [Keras] [TensorFlow 后端]

如何从零使用 Keras + TensorFlow 开发一个复杂深度学习模型?

如何为 keras 模型使用 tensorflow 自定义损失?

Keras + Tensorflow 和 Python 中的多处理