使用keras的CNN结果不一致

时间:2019-02-22 13:37:08

标签: python tensorflow keras

我已经根据使用CNN的Keras中的图像对汽车损害的严重程度进行了预测。每次我为同一数据集运行代码且没有其他参数更改时,预测的类和准确性都会更改。我尝试重新启动内核,并为模型设置种子,以期获得一致的结果。我是python新手,所以请每次都获得相同的结果。

import random
random.seed(801)
# Importing the Keras libraries and packages
from keras.models import Sequential
from keras.layers import Conv2D
from keras.layers import MaxPooling2D
from keras.layers import Flatten
from keras.layers import Dense
from keras.layers import Dropout

# Initialising the CNN
classifier = Sequential()

# Step 1 - Convolution
classifier.add(Conv2D(64, (2, 2), input_shape = (64, 64, 3), activation = 'relu'))

# Step 2 - Pooling
classifier.add(MaxPooling2D(pool_size = (2, 2)))



# Adding a second convolutional layer
classifier.add(Conv2D(64, (2, 2), activation = 'relu'))
classifier.add(MaxPooling2D(pool_size = (2, 2)))





# Step 3 - Flattening
classifier.add(Flatten())


# Adding dropout
classifier.add(Dropout(0.2))

# Step 4 - Full connection
classifier.add(Dense(units = 128, activation = 'relu'))

# Adding dropout
classifier.add(Dropout(0.2))

classifier.add(Dense(units = 1, activation = 'sigmoid'))

# Compiling the CNN
classifier.compile(optimizer = 'adam', loss = 'binary_crossentropy', metrics = ['accuracy'])

# Part 2 - Fitting the CNN to the images

from keras.preprocessing.image import ImageDataGenerator

train_datagen = ImageDataGenerator(rescale = 1./255,
                                  # shear_range = 0.2,
                                  # zoom_range = 0.2,
                                   horizontal_flip = True)

test_datagen = ImageDataGenerator(rescale = 1./255)

#train_labels = keras.utils.to_categorical(train_labels,num_classes)
#test_labels = keras.utils.to_categorical(test_labels,num_classes)

training_set = train_datagen.flow_from_directory('C:/Users/Allianz/Desktop/Image Processing/car-damage-detective-neokt/app/2 category/training',
                                                 target_size = (64, 64),
                                                 batch_size = 16,
                                                 class_mode = 'binary')


test_set = test_datagen.flow_from_directory('C:/Users/Allianz/Desktop/Image Processing/car-damage-detective-neokt/app/2 category/validation',
                                            target_size = (64, 64),
                                            batch_size = 16,
                                            class_mode = 'binary')

batch_size=16

classifier.fit_generator(training_set,
                         steps_per_epoch = 605//batch_size,
                         epochs = 9,
                         validation_data = test_set,
                         validation_steps = 5//batch_size
                         )

#classifier.save('first_model.h5')
classifier.save('first.h5')



# finding the number associated classes 
#classes=training_set.class_indices
#print(classes)

# extracting file names of images
import os
from PIL import Image
import numpy as np
path='C:/Users/Allianz/Desktop/Image Processing/car-damage-detective-neokt/app/data3a_full/validation/01-minor'
img_names = [f for f in os.listdir(path) if os.path.splitext(f)[-1] == '.JPEG']
#print(img_names[1])
img_names=np.asarray(img_names) #converting list to array


# predicting classes for multiple images
import numpy as np
from keras.models import load_model
from keras.preprocessing import image

#os.chdir('C:/Users/Allianz/Desktop/Image Processing/car-damage-detective-neokt/app/2nd check/pred')
os.chdir('C:/Users/Allianz/Desktop/Image Processing/car-damage-detective-neokt/app/data3a_full/validation/01-minor')
a=load_model('first.h5')
classes=[]
result=[]
for i in range(len(img_names)):

    img=image.load_img(img_names[i],
                   target_size=(64,64))
    test_image = image.img_to_array(img)
    test_image = np.expand_dims(test_image, axis = 0)
    result = a.predict(test_image)
    #print(result)
    if result[0] >= 0.5:
        prediction = 'severe'
    else:
        prediction = 'not severe'
    classes.append(prediction)
#print(classes) 

#prediction2=print(classes)

import pandas as pd

dfn=pd.DataFrame({'image':img_names,
                     'prediction':classes
                    })

len(dfn.loc[dfn['prediction']=='not severe'])
len(dfn.loc[dfn['prediction']=='severe'])

2 个答案:

答案 0 :(得分:0)

我在装载重物时遇到了类似的问题。问题是,当您加载权重时,由于模型声明,keras会随机分配权重。我改用检查点存储权重,并使用model.load_weights(checkpoints_directory)加载权重。您将为此使用回调。这是此任务的简短代码片段(Google上有一个很好的有关他的主题的视频)。

from keras.callbacks import ModelCheckpoint

callbacks = [ModelCheckpoint(checkpoints_directory, monitor='val_loss', save_weights_only=True, save_best_only=True, period=period)]

model.fit(..., callbacks=callbacks, ...)

答案 1 :(得分:0)

您似乎在每次分类时都在训练模型!这就是导致不一致的原因。尽管设置了种子,但仍会产生不同结果的原因可以在这里找到[Why can't I get reproducible results in Keras even though I set the random seeds?

我建议您将两个文件分开,以便在一个脚本中进行训练并在另一个脚本中进行加载然后进行测试。这样,您将获得更一致的结果。