Keras的推论损失和前向传播不匹配

时间:2019-10-12 06:10:18

标签: python tensorflow keras resnet

enter image description here

我正在使用Keras预训练模型ResNet50训练自己的日期集,该日期集仅包含一个用于测试目的的图像。首先,我用我的图像评估模型,损失为0.5,准确度为1。然后,拟合模型,损失为6,准确度为0。正向传播不匹配。看来Keras中的推断和前向传播行为是不同的。我已经附上了我的代码片段及其屏幕截图。

<form id="form2" method="post" enctype="multipart/form-data">
    <textarea name="post_content" placeholder="Content"></textarea>
    <input type="file" name="fileToUpload" id="fileToUpload">
    <br>
    <input id="sub1" type="submit" value="Upload Pic" name="uploadPic">
    <br
    />
</form>

<?php

$username = trim(isset($_SESSION['username']) ? $_SESSION['username'] : "");
$pic_name = isset($_SESSION['pic_name']) ? $_SESSION['pic_name'] : "";

if (!empty($username)) {

    $pic_name="";
    if (isset($_FILES['fileToUpload'])) {
        $errors = array();
        $file_name = $_FILES['fileToUpload']['name'];
        $file_size = $_FILES['fileToUpload']['size'];
        $width = 200;
        $height = 200;
        $file_tmp = $_FILES['fileToUpload']['tmp_name'];
        $file_type = $_FILES['fileToUpload']['type'];
        $tmp = explode('.', $_FILES['fileToUpload']['name']);
        $file_ext = strtolower(end($tmp));

        $extensions = array("jpeg", "jpg", "png");

        if (in_array($file_ext, $extensions) === false) {
            $errors[] = "Please choose a JPEG or PNG file.";
        }

        if ($file_size > 8097152) {
            $errors[] = 'File size must be 2 MB';
        }

        if ($width > 200 || $height > 200) {
            echo "File is to large";
        }

        if (empty($errors) == true) {
            $pic_name = $file_name;
            move_uploaded_file($file_tmp, "uploads/" . $pic_name);

        }
    } else {
        print_r($errors);
        echo "Couldn't upload picture";
    }
    $post_content=$_POST['post_content'];

    $stmt = $conn -> prepare("INSERT INTO pics (username, pic_name,post_content) VALUES(?, ?,?)");
    $stmt -> bind_param('sss', $username, $pic_name,$post_content);

    /* execute prepared statement */
    $stmt -> execute();

    printf("", $conn -> affected_rows);

    /* close statement and connection */

} else {
    echo "Invalid Username";
}
?>
  

1/1 [==============================]-1s 547ms / step   [0.5232877135276794,1.0]

model = ResNet50(weights='imagenet')

img_path = 'elephant.jpg'
img = image.load_img(img_path, target_size=(224, 224))
x = image.img_to_array(img)
x = np.expand_dims(x, axis=0)
x = preprocess_input(x)

y = np.zeros((1, 1000))
y[0, 386] = 1

model.compile(loss='categorical_crossentropy', optimizer='sgd', metrics=['categorical_accuracy'])

model.evaluate(x, y)
  

训练1个样本,验证1个样本时期1/1 1/1   [=============================]-3s 3s / step-损失:6.1883-   类别准确度:0.0000e + 00-损失值:9.8371e-04-   val_categorical_accuracy:1.0000

model.fit(x, y, validation_data=(x, y))
  

1/1 [==============================]-0s 74ms / step   [0.0009837078396230936,1.0]

1 个答案:

答案 0 :(得分:0)

很抱歉首先误解了这个问题。这个问题非常棘手。问题很可能是由批处理层引起的,就像评论中提到的@Natthaphon一样,因为我在VGG16上尝试过,损失是匹配的。

然后,我在ResNet50中进行了测试,即使我“冻结”了所有层,评估损失和拟合损失仍然不匹配。实际上,我手动检查了BN权重,它们的确没有改变。

from keras.applications import ResNet50, VGG16
from keras.applications.resnet50 import preprocess_input
from keras_preprocessing import image
import keras
from keras import backend as K
import numpy as np

img_path = '/home/zhihao/Downloads/elephant.jpeg'
img = image.load_img(img_path, target_size=(224, 224))

model = ResNet50(weights='imagenet')

for layer in model.layers:
    layer.trainable = False

x = image.img_to_array(img)
x = np.expand_dims(x, axis=0)
x = preprocess_input(x)

y = np.zeros((1, 1000))
y[0, 386] = 1

model.compile(loss='categorical_crossentropy', optimizer='sgd', metrics=['categorical_accuracy'])

model.evaluate(x, y)
# 1/1 [==============================] - 2s 2s/step
# [0.2981376349925995, 1.0]

model.fit(x, y, validation_data=(x, y))
# Train on 1 samples, validate on 1 samples
# Epoch 1/1
# 1/1 [==============================] - 1s 549ms/step - loss: 5.3056 - categorical_accuracy: 0.0000e+00 - val_loss: 0.2981 - val_categorical_accuracy: 1.0000

我们可以看到评估损失为0.2981,拟合损失为5.3056。我想批处理规范层在 eval 模式和 train 模式之间具有不同的行为。如果我错了纠正我。

一种真正冻结我发现的模型的方法是使用K.set_learning_phase(0),如下所示

model = ResNet50(weights='imagenet')

K.set_learning_phase(0)  # all new operations will be in test mode from now on

model.fit(x, y, validation_data=(x, y))

# Train on 1 samples, validate on 1 samples
# Epoch 1/1
# 1/1 [==============================] - 4s 4s/step - loss: 0.2981 - categorical_accuracy: 1.0000 - val_loss: 16.1181 - val_categorical_accuracy: 0.0000e+00

现在两个损失相匹配。