机器学习--环境空气质量雾霾识别
(一)选题背景:
空气质量,即反应空气污染程度的指标。它是依据空气中污染物浓度的高低来判断的,当空气中污染物浓度过高时极易产生雾霾天气。雾霾主要影响包括空气的质量与能见度,对于人体也存在一定危害。我国雾霾天气问题突出,全国已设1436个国家空气质量监测站点,由国家统一运行维护,监测数据直报国家并对外公开。然而,虽然如此,由于维护管理不善导致的数据质量问题以及层出不穷的数据造假事件,让人们对官方公布的数据不甚信任。那我们是否有一个更为直观可信赖的方法来对环境空气质量雾霾天气进行直接识别,可监控不同时期空气质量变化,从而对污染管控、削减污染峰值提出措施建议。
(二)机器学习设计案例设计方案:
从网站中下载相关的数据集,对数据集进行整理,在python的环境中,统计数据集中的文件个数,对数据进行预处理,利用keras,构建网络,训练模型,导入图片测试模型
参考来源:kaggle关于标签学习的讨论区
数据集来源:kaggle,网址:https://www.kaggle.com/datasets/ekojsalim/ohaze-patches
(三)机器学习的实现步骤:
1、数据集的下载

2、显示数据集个数
import os train_path="E:\\python\\o-hazy\\train/" #无雾霾(clean) print('total training clean_images:', len(os.listdir(train_path+"clean"))) #有雾霾(hazy) print('total training hazy_images:', len(os.listdir(train_path+"hazy"))) valid_path="E:\\python\\o-hazy\\validation/" print('total validation clean_images:', len(os.listdir(valid_path+"clean"))) print('total validation hazy_images:', len(os.listdir(valid_path+"hazy"))) test="E:\\python\\o-hazy\\test/" print('total test clean_images:', len(os.listdir(test+"clean"))) print('total test hazy_images:', len(os.listdir(test+"hazy")))

3、搭建卷积神经网络模型
from keras import layers from keras import models model = models.Sequential() #Output shape计算公式:(输入尺寸-卷积核尺寸/步长+1 #对CNN模型,Param的计算方法如下: #卷积核长度*卷积核宽度*通道数+1)*卷积核个数 # 输出图片尺寸:150-3+1=148*148 (输入尺寸-卷积核尺寸/步长+1 #参数数量:32*3*3*3+32=896 ,32是卷积核个数 model.add(layers.Conv2D(32, (3, 3), activation='relu', input_shape=(150, 150, 3))) """ 输入:参数为0 输出: Layer (type) Output Shape Param # ================================================================= conv2d_12 (Conv2D) (None, 148, 148, 32) 896 """ model.add(layers.MaxPooling2D((2, 2))) # 输出图片尺寸:148/2=74*74 """ Max_pooling_2d:此层用于减小输入图像的大小。kernal_size =(2,2)在这里使用。 因此输入图像148减少到一半74。模型从这一层学不到任何东西。 池化层中没有可以学习的参数。该层仅用于减小图像尺寸。 Layer (type) Output Shape Param # ================================================================= max_pooling2d_12 (MaxPooling (None, 74, 74, 32) 0 _________________________________________________________________ """ # 输出图片尺寸:74-3+1=72*72,参数数量:64*3*3*32+64=18496 #32是第1个卷积层的输出的通道数 model.add(layers.Conv2D(64, (3, 3), activation='relu')) """ Layer (type) Output Shape Param # ================================================================= conv2d_13 (Conv2D) (None, 72, 72, 64) 18496 _________________________________________________________________ """ model.add(layers.MaxPooling2D((2, 2))) # 输出图片尺寸:72/2=36*36 #Output Shape的输出为36 # 输出图片尺寸:36-3+1=34*34,参数数量:128*3*3*64+128=73856 model.add(layers.Conv2D(128, (3, 3), activation='relu')) model.add(layers.MaxPooling2D((2, 2))) # 输出图片尺寸:34/2=17*17 # 输出图片尺寸:17-3+1=15*15,参数数量:128*3*3*128+128=147584 model.add(layers.Conv2D(128, (3, 3), activation='relu')) model.add(layers.MaxPooling2D((2, 2))) # 输出图片尺寸:15/2=7*7 # 多维转为一维:7*7*128=6272 model.add(layers.Flatten()) # 参数数量:6272*512+512=3211776 model.add(layers.Dense(512, activation='relu')) # 参数数量:512*1+1=513 model.add(layers.Dense(1, activation='sigmoid'))
4、看一下特征图的维度如何随着每层变化
model.summary()

5、编译模型并进行图像预处理
# 编译模型 # RMSprop 优化器。因为网络最后一层是单一sigmoid单元, # 所以使用二元交叉熵作为损失函数 from keras import optimizers model.compile(loss='binary_crossentropy', optimizer=optimizers.RMSprop(lr=1e-4), metrics=['acc']) #图像在输入神经网络之前进行数据处理,建立训练和验证数据 from keras.preprocessing.image import ImageDataGenerator #归一化 train_datagen = ImageDataGenerator(rescale = 1./255) test_datagen = ImageDataGenerator(rescale = 1./255) train_dir = 'E:\\python\\o-hazy\\train/' #指向训练集图片目录路径 train_generator = train_datagen.flow_from_directory( train_dir, target_size = (150,150),# 输入训练图像尺寸 batch_size = 20, class_mode = 'binary') # validation_dir = 'E:\\python\\o-hazy\\validation/' #指向验证集图片目录路径 validation_generator = test_datagen.flow_from_directory( validation_dir, target_size = (150,150), batch_size = 20, class_mode = 'binary') for data_batch,labels_batch in train_generator: print('data batch shape:',data_batch.shape) print('data batch shape:',labels_batch.shape) break #生成器不会停止,会循环生成这些批量,所以我们就循环生成一次批量

6、对模型进行训练10轮次
#训练模型10轮次 history = model.fit( train_generator, steps_per_epoch = 100, epochs = 10, validation_data = validation_generator, validation_steps = 50)

7、数据保存为h5文件
# 将训练过程产生的数据保存为h5文件 from keras.models import load_model model.save('E:\python\o-hazy/o-hazy_10.h5')
8、绘制损失曲线和精度曲线图
# 分别绘制训练过程中模型在训练数据和验证数据上的损失和精度 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) figure, axis = plt.subplots(nrows=1, ncols=2, figsize=(18, 6)) axis[0].plot(epochs, acc, 'bo', label='Training acc') axis[0].plot(epochs, val_acc, 'b', label='Validation acc') axis[0].set_title('Training and Validation accuracy') axis[0].legend() axis[1].plot(epochs, loss, 'bo', label='Training loss') axis[1].plot(epochs, val_loss, 'b', label='Validation loss') axis[1].set_title('Training and Validation loss') axis[1].legend()

9、从测试集中读取一条样本并显示
#从测试集中读取一条样本 from keras.utils import image_utils import numpy as np img_path = "E:\\python\\o-hazy\\test\\hazy\\1.jpg" img = image_utils.load_img(img_path, target_size=(150,150)) img_tensor = image_utils.img_to_array(img) img_tensor = np.expand_dims(img_tensor, axis=0) img_tensor /= 255. print(img_tensor.shape) #显示样本 import matplotlib.pyplot as plt plt.imshow(img_tensor[0]) plt.show()

10、建立模型,输入为原图像,输出为原模型的前8层的激活输出的特征图
#建立模型,输入为原图像,输出为原模型的前8层的激活输出的特征图 from keras import models layer_outputs = [layer.output for layer in model.layers[:8]] activation_model = models.Model(inputs=model.input, outputs=layer_outputs) #获得改样本的特征图 activations = activation_model.predict(img_tensor) #显示第一层激活输出特的第一个滤波器的特征图 import matplotlib.pyplot as plt first_layer_activation = activations[0] plt.matshow(first_layer_activation[0,:,:,1], cmap="viridis")

11、显示8层激活输出的全部特征图
#存储层的名称 layer_names = [] for layer in model.layers[:4]: layer_names.append(layer.name) # 每行显示16个特征图 images_pre_row = 16 #每行显示的特征图数 # 循环8次显示8层的全部特征图 for layer_name, layer_activation in zip(layer_names, activations): n_features = layer_activation.shape[-1] #保存当前层的特征图个数 size = layer_activation.shape[1] #保存当前层特征图的宽高 n_col = n_features // images_pre_row #计算当前层显示多少行 #生成显示图像的矩阵 display_grid = np.zeros((size*n_col, images_pre_row*size)) #遍历将每个特张图的数据写入到显示图像的矩阵中 for col in range(n_col): for row in range(images_pre_row): #保存该张特征图的矩阵(size,size,1) channel_image = layer_activation[0,:,:,col*images_pre_row+row] #为使图像显示更鲜明,作一些特征处理 channel_image -= channel_image.mean() channel_image /= channel_image.std() channel_image *= 64 channel_image += 128 #把该特征图矩阵中不在0-255的元素值修改至0-255 channel_image = np.clip(channel_image, 0, 255).astype("uint8") #该特征图矩阵填充至显示图像的矩阵中 display_grid[col*size:(col+1)*size, row*size:(row+1)*size] = channel_image scale = 1./size #设置该层显示图像的宽高 plt.figure(figsize=(scale*display_grid.shape[1],scale*display_grid.shape[0])) plt.title(layer_name) plt.grid(False) #显示图像 plt.imshow(display_grid, aspect="auto", cmap="viridis")

12、导入图片进行预测
#读取用户自定义图像文件,改尺寸后保存 import matplotlib.pyplot as plt from PIL import Image import os.path def convertjpg(jpgfile,outdir,width=150,height=150):#将图片缩小到(150,150)的大小 img=Image.open(jpgfile) try: new_img=img.resize((width,height),Image.BILINEAR) new_img.save(os.path.join(outdir,os.path.basename(jpgfile))) except Exception as e: print(e) jpgfile = 'E:\\python\\o-hazy\\test\\hazy/2.jpg'#读取原图像(有雾霾) convertjpg(jpgfile,"E:\\python\\o-hazy\\working")#图像大小改变到(150,150) img_scale = plt.imread('E:\\python\\o-hazy\\working/2.jpg') plt.imshow(img_scale) #显示改变图像大小后的图片确实变到了(150,150)大小 from keras.models import load_model model = load_model('E:\python\o-hazy/o-hazy_10.h5') img_scale = img_scale.reshape(1,150,150,3).astype('float32') img_scale = img_scale/255 #归一化到0-1之间 result = model.predict(img_scale) #取图片信息 # print(result) if result>0.5: print('该图片是有雾霾的概率为:',result) else: print('该图片是无雾霾的概率为:',1-result)

#读取用户自定义图像文件,改尺寸后保存 import matplotlib.pyplot as plt from PIL import Image import os.path def convertjpg(jpgfile,outdir,width=150,height=150):#将图片缩小到(150,150)的大小 img=Image.open(jpgfile) try: new_img=img.resize((width,height),Image.BILINEAR) new_img.save(os.path.join(outdir,os.path.basename(jpgfile))) except Exception as e: print(e) jpgfile = 'E:\\python\\o-hazy\\test\\clean/2.jpg'#读取原图像(无雾霾) convertjpg(jpgfile,"E:\\python\\o-hazy\\working")#图像大小改变到(150,150) img_scale = plt.imread('E:\\python\\o-hazy\\working/12.jpg') plt.imshow(img_scale) #显示改变图像大小后的图片确实变到了(150,150)大小 from keras.models import load_model model = load_model('E:\python\o-hazy/o-hazy_10.h5') img_scale = img_scale.reshape(1,150,150,3).astype('float32') img_scale = img_scale/255 #归一化到0-1之间 result = model.predict(img_scale) #取图片信息 # print(result) if result>0.5: print('该图片是有雾霾的概率为:',result) else: print('该图片是无雾霾的概率为:',1-result)

13、用测试集对模型进行测试
# 用测试集对模型进行测试: test_datagen = ImageDataGenerator(rescale = 1./255) test_dir='E:\\python\\o-hazy\\test' 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=test_generator.samples // 20) print('test acc:', test_acc)

14、更改训练50轮次
#训练模型50轮次 history = model.fit( train_generator, steps_per_epoch = 100, epochs = 50, validation_data = validation_generator, validation_steps = 50)

15、训练过程产生的数据保存为h5文件
# 将训练过程产生的数据保存为h5文件 from keras.models import load_model model.save('E:\python\o-hazy/o-hazy_50.h5')
16、绘制损失曲线和精度曲线图
# 分别绘制训练过程中模型在训练数据和验证数据上的损失和精度 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) figure, axis = plt.subplots(nrows=1, ncols=2, figsize=(18, 6)) axis[0].plot(epochs, acc, 'bo', label='Training acc') axis[0].plot(epochs, val_acc, 'b', label='Validation acc') axis[0].set_title('Training and Validation accuracy') axis[0].legend() axis[1].plot(epochs, loss, 'bo', label='Training loss') axis[1].plot(epochs, val_loss, 'b', label='Validation loss') axis[1].set_title('Training and Validation loss') axis[1].legend()

17、导入图片进行预测
#读取用户自定义图像文件,改尺寸后保存 import matplotlib.pyplot as plt from PIL import Image import os.path def convertjpg(jpgfile,outdir,width=150,height=150):#将图片缩小到(150,150)的大小 img=Image.open(jpgfile) try: new_img=img.resize((width,height),Image.BILINEAR) new_img.save(os.path.join(outdir,os.path.basename(jpgfile))) except Exception as e: print(e) jpgfile = 'E:\\python\\o-hazy\\test\\hazy/2.jpg'#读取原图像(有雾霾) convertjpg(jpgfile,"E:\\python\\o-hazy\\working")#图像大小改变到(150,150) img_scale = plt.imread('E:\\python\\o-hazy\\working/2.jpg') plt.imshow(img_scale) #显示改变图像大小后的图片确实变到了(150,150)大小 from keras.models import load_model model = load_model('E:\python\o-hazy/o-hazy_50.h5') img_scale = img_scale.reshape(1,150,150,3).astype('float32') img_scale = img_scale/255 #归一化到0-1之间 result = model.predict(img_scale) #取图片信息 # print(result) if result>0.5: print('该图片是有雾霾的概率为:',result) else: print('该图片是无雾霾的概率为:',1-result)

#读取用户自定义图像文件,改尺寸后保存 import matplotlib.pyplot as plt from PIL import Image import os.path def convertjpg(jpgfile,outdir,width=150,height=150):#将图片缩小到(150,150)的大小 img=Image.open(jpgfile) try: new_img=img.resize((width,height),Image.BILINEAR) new_img.save(os.path.join(outdir,os.path.basename(jpgfile))) except Exception as e: print(e) jpgfile = 'E:\\python\\o-hazy\\test\\clean/2.jpg'#读取原图像(无雾霾) convertjpg(jpgfile,"E:\\python\\o-hazy\\working")#图像大小改变到(150,150) img_scale = plt.imread('E:\\python\\o-hazy\\working/2.jpg') plt.imshow(img_scale) #显示改变图像大小后的图片确实变到了(150,150)大小 from keras.models import load_model model = load_model('E:\python\o-hazy/o-hazy_50.h5') img_scale = img_scale.reshape(1,150,150,3).astype('float32') img_scale = img_scale/255 #归一化到0-1之间 result = model.predict(img_scale) #取图片信息 # print(result) if result>0.5: print('该图片是有雾霾的概率为:',result) else: print('该图片是无雾霾的概率为:',1-result)

18、用测试集对模型进行测试
# 用测试集对模型进行测试: test_datagen = ImageDataGenerator(rescale = 1./255) test_dir='E:\\python\\o-hazy\\test' 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=test_generator.samples // 20) print('test acc:', test_acc)

19、附上全部代码:
1 #显示数据集个数 2 import os 3 4 train_path="E:\\python\\o-hazy\\train/" 5 #无雾霾(clean) 6 print('total training clean_images:', len(os.listdir(train_path+"clean"))) 7 #有雾霾(hazy) 8 print('total training hazy_images:', len(os.listdir(train_path+"hazy"))) 9 10 valid_path="E:\\python\\o-hazy\\validation/" 11 print('total validation clean_images:', len(os.listdir(valid_path+"clean"))) 12 print('total validation hazy_images:', len(os.listdir(valid_path+"hazy"))) 13 14 test="E:\\python\\o-hazy\\test/" 15 print('total test clean_images:', len(os.listdir(test+"clean"))) 16 print('total test hazy_images:', len(os.listdir(test+"hazy"))) 17 18 #搭建卷积神经网络模型 19 from keras import layers 20 from keras import models 21 22 model = models.Sequential() 23 24 #Output shape计算公式:(输入尺寸-卷积核尺寸/步长+1 25 26 #对CNN模型,Param的计算方法如下: 27 28 #卷积核长度*卷积核宽度*通道数+1)*卷积核个数 29 30 # 输出图片尺寸:150-3+1=148*148 (输入尺寸-卷积核尺寸/步长+1 31 32 #参数数量:32*3*3*3+32=896 ,32是卷积核个数 33 model.add(layers.Conv2D(32, (3, 3), activation='relu', input_shape=(150, 150, 3))) 34 35 """ 36 输入:参数为0 37 输出: 38 Layer (type) Output Shape Param # 39 ================================================================= 40 conv2d_12 (Conv2D) (None, 148, 148, 32) 896 41 42 """ 43 44 model.add(layers.MaxPooling2D((2, 2))) # 输出图片尺寸:148/2=74*74 45 46 """ 47 48 Max_pooling_2d:此层用于减小输入图像的大小。kernal_size =(2,2)在这里使用。 49 因此输入图像148减少到一半74。模型从这一层学不到任何东西。 50 池化层中没有可以学习的参数。该层仅用于减小图像尺寸。 51 Layer (type) Output Shape Param # 52 ================================================================= 53 max_pooling2d_12 (MaxPooling (None, 74, 74, 32) 0 54 _________________________________________________________________ 55 56 """ 57 58 # 输出图片尺寸:74-3+1=72*72,参数数量:64*3*3*32+64=18496 59 #32是第1个卷积层的输出的通道数 60 model.add(layers.Conv2D(64, (3, 3), activation='relu')) 61 62 """ 63 Layer (type) Output Shape Param # 64 ================================================================= 65 conv2d_13 (Conv2D) (None, 72, 72, 64) 18496 66 _________________________________________________________________ 67 """ 68 69 model.add(layers.MaxPooling2D((2, 2))) # 输出图片尺寸:72/2=36*36 70 71 #Output Shape的输出为36 72 # 输出图片尺寸:36-3+1=34*34,参数数量:128*3*3*64+128=73856 73 model.add(layers.Conv2D(128, (3, 3), activation='relu')) 74 model.add(layers.MaxPooling2D((2, 2))) # 输出图片尺寸:34/2=17*17 75 76 # 输出图片尺寸:17-3+1=15*15,参数数量:128*3*3*128+128=147584 77 model.add(layers.Conv2D(128, (3, 3), activation='relu')) 78 model.add(layers.MaxPooling2D((2, 2))) # 输出图片尺寸:15/2=7*7 79 80 # 多维转为一维:7*7*128=6272 81 model.add(layers.Flatten()) 82 83 # 参数数量:6272*512+512=3211776 84 model.add(layers.Dense(512, activation='relu')) 85 86 # 参数数量:512*1+1=513 87 model.add(layers.Dense(1, activation='sigmoid')) 88 89 #看一下特征图的维度如何随着每层变化 90 model.summary() 91 92 # 编译模型 93 # RMSprop 优化器。因为网络最后一层是单一sigmoid单元, 94 # 所以使用二元交叉熵作为损失函数 95 from keras import optimizers 96 97 model.compile(loss='binary_crossentropy', 98 optimizer=optimizers.RMSprop(lr=1e-4), 99 metrics=['acc']) 100 101 #图像在输入神经网络之前进行数据处理,建立训练和验证数据 102 from keras.preprocessing.image import ImageDataGenerator 103 104 #归一化 105 train_datagen = ImageDataGenerator(rescale = 1./255) 106 test_datagen = ImageDataGenerator(rescale = 1./255) 107 108 train_dir = 'E:\\python\\o-hazy\\train/' #指向训练集图片目录路径 109 110 train_generator = train_datagen.flow_from_directory( 111 train_dir, 112 target_size = (150,150),# 输入训练图像尺寸 113 batch_size = 20, 114 class_mode = 'binary') # 115 116 validation_dir = 'E:\\python\\o-hazy\\validation/' #指向验证集图片目录路径 117 118 validation_generator = test_datagen.flow_from_directory( 119 validation_dir, 120 target_size = (150,150), 121 batch_size = 20, 122 class_mode = 'binary') 123 124 for data_batch,labels_batch in train_generator: 125 print('data batch shape:',data_batch.shape) 126 print('data batch shape:',labels_batch.shape) 127 break #生成器不会停止,会循环生成这些批量,所以我们就循环生成一次批量 128 129 #训练模型10轮次 130 history = model.fit( 131 train_generator, 132 steps_per_epoch = 100, 133 epochs = 10, 134 validation_data = validation_generator, 135 validation_steps = 50) 136 137 # 将训练过程产生的数据保存为h5文件 138 from keras.models import load_model 139 model.save('E:\python\o-hazy/o-hazy_10.h5') 140 141 # 分别绘制训练过程中模型在训练数据和验证数据上的损失和精度 142 import matplotlib.pyplot as plt 143 144 acc = history.history['acc'] 145 val_acc = history.history['val_acc'] 146 loss = history.history['loss'] 147 val_loss = history.history['val_loss'] 148 149 epochs = range(1, len(acc) + 1) 150 151 figure, axis = plt.subplots(nrows=1, ncols=2, figsize=(18, 6)) 152 axis[0].plot(epochs, acc, 'bo', label='Training acc') 153 axis[0].plot(epochs, val_acc, 'b', label='Validation acc') 154 axis[0].set_title('Training and Validation accuracy') 155 axis[0].legend() 156 157 axis[1].plot(epochs, loss, 'bo', label='Training loss') 158 axis[1].plot(epochs, val_loss, 'b', label='Validation loss') 159 axis[1].set_title('Training and Validation loss') 160 axis[1].legend() 161 162 #从测试集中读取一条样本 163 from keras.utils import image_utils 164 import numpy as np 165 img_path = "E:\\python\\o-hazy\\test\\hazy\\1.jpg" 166 img = image_utils.load_img(img_path, target_size=(150,150)) 167 img_tensor = image_utils.img_to_array(img) 168 img_tensor = np.expand_dims(img_tensor, axis=0) 169 img_tensor /= 255. 170 print(img_tensor.shape) 171 172 #显示样本 173 import matplotlib.pyplot as plt 174 plt.imshow(img_tensor[0]) 175 plt.show() 176 177 #建立模型,输入为原图像,输出为原模型的前8层的激活输出的特征图 178 from keras import models 179 180 layer_outputs = [layer.output for layer in model.layers[:8]] 181 activation_model = models.Model(inputs=model.input, outputs=layer_outputs) 182 #获得改样本的特征图 183 activations = activation_model.predict(img_tensor) 184 185 #显示第一层激活输出特的第一个滤波器的特征图 186 import matplotlib.pyplot as plt 187 first_layer_activation = activations[0] 188 plt.matshow(first_layer_activation[0,:,:,1], cmap="viridis") 189 190 #存储层的名称 191 layer_names = [] 192 for layer in model.layers[:4]: 193 layer_names.append(layer.name) 194 # 每行显示16个特征图 195 images_pre_row = 16 #每行显示的特征图数 196 # 循环8次显示8层的全部特征图 197 for layer_name, layer_activation in zip(layer_names, activations): 198 n_features = layer_activation.shape[-1] #保存当前层的特征图个数 199 size = layer_activation.shape[1] #保存当前层特征图的宽高 200 n_col = n_features // images_pre_row #计算当前层显示多少行 201 #生成显示图像的矩阵 202 display_grid = np.zeros((size*n_col, images_pre_row*size)) 203 #遍历将每个特张图的数据写入到显示图像的矩阵中 204 for col in range(n_col): 205 for row in range(images_pre_row): 206 #保存该张特征图的矩阵(size,size,1) 207 channel_image = layer_activation[0,:,:,col*images_pre_row+row] 208 #为使图像显示更鲜明,作一些特征处理 209 channel_image -= channel_image.mean() 210 channel_image /= channel_image.std() 211 channel_image *= 64 212 channel_image += 128 213 #把该特征图矩阵中不在0-255的元素值修改至0-255 214 channel_image = np.clip(channel_image, 0, 255).astype("uint8") 215 #该特征图矩阵填充至显示图像的矩阵中 216 display_grid[col*size:(col+1)*size, row*size:(row+1)*size] = channel_image 217 218 scale = 1./size 219 #设置该层显示图像的宽高 220 plt.figure(figsize=(scale*display_grid.shape[1],scale*display_grid.shape[0])) 221 plt.title(layer_name) 222 plt.grid(False) 223 #显示图像 224 plt.imshow(display_grid, aspect="auto", cmap="viridis") 225 226 #读取用户自定义图像文件,改尺寸后保存 227 228 import matplotlib.pyplot as plt 229 from PIL import Image 230 import os.path 231 232 def convertjpg(jpgfile,outdir,width=150,height=150):#将图片缩小到(150,150)的大小 233 img=Image.open(jpgfile) 234 try: 235 new_img=img.resize((width,height),Image.BILINEAR) 236 new_img.save(os.path.join(outdir,os.path.basename(jpgfile))) 237 except Exception as e: 238 print(e) 239 240 jpgfile = 'E:\\python\\o-hazy\\test\\hazy/2.jpg'#读取原图像(有雾霾) 241 convertjpg(jpgfile,"E:\\python\\o-hazy\\working")#图像大小改变到(150,150) 242 img_scale = plt.imread('E:\\python\\o-hazy\\working/2.jpg') 243 plt.imshow(img_scale) #显示改变图像大小后的图片确实变到了(150,150)大小 244 from keras.models import load_model 245 model = load_model('E:\python\o-hazy/o-hazy_10.h5') 246 247 img_scale = img_scale.reshape(1,150,150,3).astype('float32') 248 img_scale = img_scale/255 #归一化到0-1之间 249 250 result = model.predict(img_scale) #取图片信息 251 # print(result) 252 if result>0.5: 253 print('该图片是有雾霾的概率为:',result) 254 else: 255 print('该图片是无雾霾的概率为:',1-result) 256 257 #读取用户自定义图像文件,改尺寸后保存 258 259 import matplotlib.pyplot as plt 260 from PIL import Image 261 import os.path 262 263 def convertjpg(jpgfile,outdir,width=150,height=150):#将图片缩小到(150,150)的大小 264 img=Image.open(jpgfile) 265 try: 266 new_img=img.resize((width,height),Image.BILINEAR) 267 new_img.save(os.path.join(outdir,os.path.basename(jpgfile))) 268 except Exception as e: 269 print(e) 270 271 jpgfile = 'E:\\python\\o-hazy\\test\\clean/2.jpg'#读取原图像(无雾霾) 272 convertjpg(jpgfile,"E:\\python\\o-hazy\\working")#图像大小改变到(150,150) 273 img_scale = plt.imread('E:\\python\\o-hazy\\working/12.jpg') 274 plt.imshow(img_scale) #显示改变图像大小后的图片确实变到了(150,150)大小 275 276 from keras.models import load_model 277 model = load_model('E:\python\o-hazy/o-hazy_10.h5') 278 279 img_scale = img_scale.reshape(1,150,150,3).astype('float32') 280 img_scale = img_scale/255 #归一化到0-1之间 281 282 result = model.predict(img_scale) #取图片信息 283 # print(result) 284 if result>0.5: 285 print('该图片是有雾霾的概率为:',result) 286 else: 287 print('该图片是无雾霾的概率为:',1-result) 288 289 # 用测试集对模型进行测试: 290 test_datagen = ImageDataGenerator(rescale = 1./255) 291 test_dir='E:\\python\\o-hazy\\test' 292 test_generator = test_datagen.flow_from_directory( 293 test_dir, 294 target_size=(150,150), 295 batch_size=20, 296 class_mode='binary') 297 298 test_loss, test_acc = model.evaluate_generator(test_generator, steps=test_generator.samples // 20) 299 print('test acc:', test_acc)
(四)总结:
结论:从以上两次不同轮次训练的测试结果可以看出,训练数据和验证数据的准确率会随着训练轮次的增加而提高。测试集精度在epochs = 10时为0.77,而在epochs = 50时为0.89,这结果相差达0.12左右。因此该模型在训练轮次上还可以继续增加即可达到最适的结果。相信继续增加训练轮次,测试准确率将不断提高,以保证测试结果数据的可靠性。
收获:随着大数据时代各行业对数据分析需求的持续增加,通过机器学习高效地获取知识,已逐渐成为当今机器学习技术发展的主要推动力。在本次机器学习的过程中,我深刻的了解了机器学习,它是人工智能的核心,更是使计算机具有智能的根本途径。本次课程设计基本实现,但不足之处在于准确率并没有达到我预期的标准,如何让准确率再提高是需要改进的地方。感谢老师本学期的教学,让我对机器学习的概念有了更进一步的学习。
浙公网安备 33010602011771号