【问题标题】:Pre-training Keras Xception and InceptionV3 models预训练 Keras Xception 和 InceptionV3 模型
【发布时间】:2018-07-31 03:21:14
【问题描述】:

我正在尝试使用 Keras 及其预构建的 ImageNet CNN 架构来解决一个简单的二元分类问题。

对于VGG16,我采取了以下方法,

vgg16_model = keras.application.vgg16.VGG16()

'''Rebuild the vgg16 using an empty sequential model'''
model = Sequential()
for layer in vgg16_model.layers:
    model.add(layer)

'''Since the problem is binary, I got rid of the output layer and added a more appropriate output layer.'''
model.pop()

'''Freeze other pre-trained weights'''
for layer in model.layers:
    layer.trainable = False

'''Add the modified final layer'''
model.add(Dense(2, activation = 'softmax'))

这比我定制的 CNN 工作得非常好,准确度更高。但是训练需要一段时间,我想使用 Xception 和 InceptionV3 采用类似的方法,因为它们是更轻的模型,精度更高。

xception_model = keras.applicaitons.xception.Xception()
model = Sequential()
for layer in xception_model.layers:
    model_xception.add(layer)

当我运行上面的代码时,我得到以下错误:

ValueError: Input 0 is incompatible with layer conv2d_193: expected axis -1 of input shape to have value 64 but got shape (None, None, None, 128)

基本上,我想做与 VGG16 模型相同的事情;保持其他预训练的权重不变,只需将输出层修改为二进制分类输出,而不是具有 1000 个结果的输出层。我可以看到,与具有相对简单的卷积层结构的 VGG16 不同,Xception 和 InceptionV3 有一些我不是 100% 熟悉的时髦节点,我假设这些节点会导致问题。

【问题讨论】:

  • 为什么你使用 softmax 来解决 2 类问题,因为它是二进制的,而你没有使用 sigmoid? output = Dense(2, activation='softmax')(base_model.output)

标签: python tensorflow deep-learning keras


【解决方案1】:

您的代码失败,因为 InceptionV3Xception 不是 Sequential 模型(即它们包含“分支”)。因此,您不能只将图层添加到 Sequential 容器中。

现在由于InceptionV3Xception 的顶层由GlobalAveragePooling2D 层和最后的Dense(1000) 层组成,

if include_top:
    x = GlobalAveragePooling2D(name='avg_pool')(x)
    x = Dense(classes, activation='softmax', name='predictions')(x)

如果你想去掉最后的密集层,你可以在创建这些模型时设置include_top=False加上pooling='avg'

base_model = InceptionV3(include_top=False, pooling='avg')
for layer in base_model.layers:
    layer.trainable = False
output = Dense(2, activation='softmax')(base_model.output)
model = Model(base_model.input, output)

【讨论】:

  • 非常感谢!有道理 Sequential 不能在有分支的网络上工作
  • 很抱歉再次打扰您,但是您能解释一下为什么我需要顺便设置 pooling = 'avg' 吗?谢谢!
  • 因为原始模型是这样做的。通过设置include_top=False,从InceptionV3中去掉两层——(1)GlobalAveragePooling2D()(2)Dense(1000)。由于您只想替换最终的Dense 层,因此您必须先添加平均池化层,然后再在其上添加新层。
  • 我想使用 Xception 概念从头开始编写代码,可以给我看示例代码
猜你喜欢
  • 1970-01-01
  • 2018-02-22
  • 2019-09-21
  • 1970-01-01
  • 2018-04-15
  • 1970-01-01
  • 2019-01-20
  • 1970-01-01
  • 2017-06-05
相关资源
最近更新 更多