VGG16模型微调fineTuning的猫狗识别

#使用vgg模型的第二种方法:载入vgg模型文件还原模型,让后将这个模型
#包含到自己的模型中,构建分类模型重新训练得到一个全新的模型保存文件。
#计算量很大CPU不可算出,精度97%。
from keras.applications import vgg16
conv_base = vgg16.VGG16(weights='imagenet',#指定模型初始化的权重检测点
                include_top=False,#模型最后是否包含密集连接分类器.
                #后添加的层在顶部
                input_shape=(150,150,3)#图像的形状,默认可以处理任意形状
                )
#下载文件到C:\Users\Administrator\.keras\models\vgg16_weights_tf_dim_ordering_tf_kernels_notop.h5
import os
import numpy as np
import json
from keras import  callbacks
from keras import models,layers,optimizers
#这个路径是在运行了_5_2中的图片复制部分后又数据的目录
base_dir = 'D:/File/Study/MachineLearning/Python深度学习/练习/vs2017/trainData/cats_and_dogs_samll'
train_dir = os.path.join(base_dir,'train')
validation_dir = os.path.join(base_dir,'validation')
test_dir = os.path.join(base_dir,'test')
history_Dir = '_5_3_2history.json'
history=callbacks.History()
from keras.preprocessing.image import ImageDataGenerator
test_datagen = ImageDataGenerator(rescale=1. / 255)
model={}
if os.path.exists(history_Dir) != True:
    #################从头训练vgg模型+自己的分类模型################
    
    model = models.Sequential()
    model.add(conv_base)
    model.add(layers.Flatten())
    model.add(layers.Dense(256,activation='relu'))
    model.add(layers.Dense(1,activation='sigmoid'))
    print(model.summary())
    #_________________________________________________________________
    #Layer (type) Output Shape Param #
    #=================================================================
    #vgg16 (Model) (None, 4, 4, 512) 14714688
    #_________________________________________________________________
    #flatten_1 (Flatten) (None, 8192) 0
    #_________________________________________________________________
    #dense_1 (Dense) (None, 256) 2097408
    #_________________________________________________________________
    #dense_2 (Dense) (None, 1) 257
    #=================================================================
    #Total params: 16,812,353
    #参数总数:1681万个
    #Trainable params: 16,812,353
    #Non-trainable params: 0
    #################################################################
    print('This is the number of trainable weights '
    'before freezing the conv base:', len(model.trainable_weights))
    conv_base.trainable = False#冻结vgg模型防止他的权重改变编译后生效
    print('This is the number of trainable weights '
    'after freezing the conv base:', len(model.trainable_weights))

    ##########################使用增强数据参数#########################
    
    train_datagen = ImageDataGenerator(rescale=1. / 255,
        rotation_range=40,
        width_shift_range=0.2,
        height_shift_range=0.2,
        shear_range=0.2,
        zoom_range=0.2,
        horizontal_flip=True,
        fill_mode='nearest')
    
    train_generator = train_datagen.flow_from_directory(train_dir,
                                                        target_size=(150,150),
                                                        batch_size=20,
                                                        class_mode='binary')        

    validation_generator = test_datagen.flow_from_directory(validation_dir,
                                                            target_size=(150,150),
                                                            batch_size=20,
                                                            class_mode='binary')
    #################################################################
    model.compile(optimizer=optimizers.RMSprop(lr=2e-5),
                  loss='binary_crossentropy',
                  metrics=['acc'])
    history = model.fit_generator(train_generator,
                                  steps_per_epoch=100,
                                  epochs=30,
                                  validation_data=validation_generator,
                                  validation_steps=50)
    #####################书上说精度约96%:我实测验证精度90%训练11分钟##############
    #可能跟我的显存总是不够有关。
    ####################使用模型微调fineTunning调整卷积基的最后几层################
    conv_base.trainable = True
    set_trainable = False
    for layer in conv_base.layers:
           if layer.name == 'block5_conv1':
               set_trainable = True
           if set_trainable:
               layer.trainable = True
           else:
               layer.trainable = False

    model.compile(loss='binary_crossentropy',
                  optimizer=optimizers.RMSprop(lr=1e-5),
                  metrics=['acc'])
    history = model.fit_generator(
        train_generator,
        steps_per_epoch=100,
        epochs=100,
        validation_data=validation_generator,
        validation_steps=50)
    model.save('_5_3_2.h5')#

###############训练时间太长了,训练一次就存起来方便还原###########
    historyStr = json.dumps(history.history)
    #history不能直接被序列化
    with open(history_Dir, 'w', encoding='utf-8') as f:
        f.write(historyStr)
        f.close()
else :
    #with open(history_Dir, encoding='utf-8') as f:
    #    history.history = json.load(f)
    #    f.close()
    model=models.load_model('_5_3_2.h5')
####################显示精度曲线和损失曲线,精度到了97%提升了1%#######################
#import matplotlib.pyplot as plt
#acc = history.history['acc']
#val_acc = history.history['val_acc']
#loss = history.history['loss']
#val_loss = history.history['val_loss']
#epochs = range(1, len(acc) + 1)
#plt.plot(epochs, acc, 'bo', label='Training acc')
#plt.plot(epochs, val_acc, 'b', label='Validation acc')
#plt.title('Training and validation accuracy')
#plt.legend()
#plt.figure()
#plt.plot(epochs, loss, 'bo', label='Training loss')
#plt.plot(epochs, val_loss, 'b', label='Validation loss')
#plt.title('Training and validation loss')
#plt.legend()
#plt.show()
######################################################################################
#使得曲线变的平滑
#def smooth_curve(points, factor=0.8):
#    smoothed_points = []
#    for point in points:
#        if smoothed_points:
#            previous = smoothed_points[-1]
#            smoothed_points.append(previous * factor + point * (1 - factor))
#        else:
#            smoothed_points.append(point)
#    return smoothed_points
#####################################################################################
#import matplotlib.pyplot as plt
#acc = history.history['acc']
#val_acc = history.history['val_acc']
#loss = history.history['loss']
#val_loss = history.history['val_loss']
#epochs = range(1, len(acc) + 1)
###################
#plt.plot(epochs, smooth_curve(acc), 'bo', label='Training acc')
#plt.plot(epochs, smooth_curve(val_acc), 'b', label='Validation acc')
#plt.title('Training and validation accuracy')
#plt.legend()
##################
#plt.figure()
#plt.plot(epochs,smooth_curve(loss), 'bo', label='Training loss')
#plt.plot(epochs, smooth_curve(val_loss), 'b', label='Validation loss')
#plt.title('Training and validation loss')
#plt.legend()
#plt.show()
##没有画出图来,训练时间太长回头再修改
#############################在测试数据上最终评估模型##########################
test_generator = test_datagen.flow_from_directory(test_dir,target_size=(150,150),
    batch_size=20,class_mode='binary')
test_loss,test_acc = model.evaluate_generator(test_generator,steps=50)
print('test acc:',test_acc)


 

你可能感兴趣的:(AI,深度学习,Keras)