python – 使用预训练的Inceptionv3提取瓶颈功能 – Keras的实现与Native Tensorflow实现之间的差异

(长篇道歉)

所有,

我想使用预训练的Inceptionv3模型的瓶颈功能来预测输入图像的分类.在训练模型和预测分类之前,我尝试了3种不同的方法来提取瓶颈功能.

我的3种方法产生了不同的瓶颈特征(不仅仅是数值,甚至大小也不同).

>我的瓶颈特征来自方法1和方法2 :(输入图像的数量)x 3 x 3 x 2048

我的瓶颈大小来自方法3 :(输入图像的数量)x 2048

为什么基于Keras的Inceptionv3模型和原生Tensorflow模型之间的大小不同?我的猜测是,当我在Keras中说include_top = False时,我没有提取’pool_3 / _reshape:0’层.它是否正确?如果是,我如何在Keras中提取’pool_3 / _reshape:0’图层?如果我的猜测不正确,我错过了什么?
>我比较了方法1和方法2的瓶颈特征值,它们有显着差异.我想我正在为它输入相同的输入图像,因为我在将其作为我的脚本的输入读取之前调整大小并重新调整我的图像.我在方法1中没有选择ImageDataGenerator,根据该函数的文档,所有默认值都不会改变我的输入图像.我已将shuffle设置为false,因此我假设predict_generator和predict是以相同的顺序读取图像.我错过了什么?

请注意:

我的输入图像是RGB格式(因此通道数= 3),我将它们全部调整为150×150.我使用inceptionv3.py中的preprocess_input函数来预处理我的所有图像.

def preprocess_input(image):
    image /= 255.
    image -= 0.5
    image *= 2.
    return image

方法1:使用带有tensorflow作为后端的Keras,用于读取我的数据的ImageDataGenerator和用于计算瓶颈功能的model.predict_generator

我跟随了Keras博客的example(使用预训练网络的瓶颈功能:一分钟内准确度达到90%).我没有列出那里列出的VGG模型,而是使用了Inceptionv3.下面是我使用的代码片段

(这里没有显示代码,但是我在下面的代码之前做了什么):读取所有输入图像,调整大小为150x150x3,根据上面提到的preprocessing_input函数重新缩放,保存调整大小和重新缩放的图像

train_datagen = ImageDataGenerator() 
train_generator = train_datagen.flow_from_directory(my_input_dir, target_size=(150,150),shuffle=False, batch_size=16)

# get bottleneck features
# use pre-trained model and exclude top layer - which is used for classification
pretrained_model = InceptionV3(include_top=False, weights='imagenet', input_shape=(150,150,3))
bottleneck_features_train_v1 = pretrained_model.predict_generator(train_generator,len(train_generator.filenames)//16)

方法2:使用带有tensorflow作为后端的Keras,我自己的reader和model.predict来计算瓶颈特征

这种方法与早期方法之间的区别仅在于我使用自己的阅读器来读取输入图像.
(这里没有显示代码,但是我在下面的代码之前做了什么):读取所有输入图像,调整大小为150x150x3,根据上面提到的preprocessing_input函数重新缩放,保存调整大小和重新缩放的图像

# inputImages is a numpy array of size <number of input images x 150 x 150 x 3>
inputImages = readAllJPEGsInFolderAndMergeAsRGB(my_input_dir)

# get bottleneck features
# use pre-trained model and exclude top layer - which is used for classification
pretrained_model = InceptionV3(include_top=False, weights='imagenet', input_shape=(img_width, img_height, 3))
bottleneck_features_train_v2 = pretrained_model.predict(trainData.images,batch_size=16)

方法3:使用张量流(NO KERAS)计算瓶颈特征

我按照retrain.py为我的输入图像提取瓶颈功能.请注意,该脚本的权重可以从(http://download.tensorflow.org/models/image/imagenet/inception-2015-12-05.tgz)获得

如该示例中所述,我使用了bottleneck_tensor_name =’pool_3 / _reshape:0’作为提取和计算瓶颈功能的图层.与前两种方法类似,我使用调整大小和重新缩放的图像作为脚本的输入,我称之为功能列表bottleneck_features_train_v3

非常感谢

最佳答案
1和2之间的结果不同

既然你没有显示你的代码,我(可能是错误地)提出问题是你在声明ImageDataGenerator时可能没有使用过preprocess_input?

from keras.applications.inception_v3 import preprocess_input

train_datagen = ImageDataGenerator(preprocessing_function=preprocess_input) 

但请确保保存的图像文件范围为0到255.(位深度24).

1到3之间的不同形状

在这种情况下,有三种可能的模型类型:

> include_top = True – >这将返回课程
> include_top = False(仅限) – >这意味着在pooling = None(没有最终的汇聚层)
> include_top = False,pooling =’avg’或=’max’ – >有一个池层

因此,没有显式池化的声明模型=某些东西在keras中没有最终的池化层.然后输出仍然具有空间维度.

只需在最后添加池即可解决这个问题.其中之一:

pretrained_model = InceptionV3(include_top=False, pooling = 'avg', weights='imagenet', input_shape=(img_width, img_height, 3))
pretrained_model = InceptionV3(include_top=False, pooling = 'max', weights='imagenet', input_shape=(img_width, img_height, 3))

不确定tgz文件中的哪个模型正在使用.

作为替代方案,您还可以从Tensorflow模型中获取另一个图层,即“pool_3”之前的图层.

转载注明原文:python – 使用预训练的Inceptionv3提取瓶颈功能 – Keras的实现与Native Tensorflow实现之间的差异 - 代码日志