keras CNN入门(一)

本文为吴恩达教授的Tensorflow实践系列课程的学习记录。


完整代码:https://github.com/YvanYan/keras/tree/master/part1-cnn

关于tensorflow的安装,网上有许多博客讲解的十分详细,本文不再叙述。

本文内容:
1.搭建一个简单的神经网络
2.实现简单的卷积神经网络
3.使用卷积神经网络处理真实图片

1.搭建一个简单的神经网络

首先加载数据集,由于国内网络环境问题,因此是通过数据集链接将数据下载到本地,再进行加载。本地数据集是IDX文件格式,因此可以通过项目中loaddata.py文件进行读取。

mnist = tf.keras.datasets.fashion_mnist
(train_imgs, train_labels), (test_imgs, test_labels) = mnist.load_data()

对数据进行归一化,因为每个像素值是0-255,所以将像素值归一化成0-1。归一化使网络更好的收敛,准确率更高。

training_images  = training_images / 255.0
test_images = test_images / 255.0

搭建训练模型。Flatten表示将二维数据变成1维,图像数据是 28* 28,通过Flatten层后就变成了 784* 1。Dense表示神经网络中的层,每一层需要指定神经元的数量激活函数神经元的数量在一定程度上可以提高准确性,但会花费更多的时间。对于简单的数据集,增加神经元的数量并不能很明显的提高准确率。激活函数可以非线性的改变上一层的输出结果,从而更好的拟合各种函数。各种常用的激活函数模型可以参考这篇博客。最后一层输出层的神经元数量为10,因为在这个数据集中,图像是十分类问题,所有需要最后有十个不同的神经元对应不同的类别。如果最后输出层的神经元数量少于分类数,会报错。

model = tf.keras.models.Sequential([tf.keras.layers.Flatten(), 
                                    tf.keras.layers.Dense(128, activation=tf.nn.relu), 
                                    tf.keras.layers.Dense(10, activation=tf.nn.softmax)])

编译、训练和评估模型。compile来编译网络,需要指明优化器和损失函数。fit来训练网络,传入训练图像、训练图像标签、训练轮次。轮次越多准确率越高,耗时越多,但简单的问题轮次越多并不表示越好,因为网络可能会过拟合,即在训练集表现极好,但对于测试集表现一般,这样的结果表示网络的泛化能力较差。evaluate来评估网络,给网络输入测试集合,测试集表示网络从没有接触过的新图像。从而测试网络的准确率。

model.compile(optimizer = tf.train.AdamOptimizer(),
              loss = 'sparse_categorical_crossentropy')

model.fit(training_images, training_labels, epochs=5)
model.evaluate(test_images, test_labels)
2.实现简单的卷积神经网络

卷积神经网络主要的层是卷积层和池化层。Conv2D第一个参数是希望生成的滤波器的数量,可以任意设置,但最好以32的倍数。第二个参数是滤波器的尺寸。第三个参数的激活函数,激活函数采用relu是因为在图像中像素不能为负数,所有relu保证了将所有的负数置为0。第四个参数为输入数据的尺寸,第一层的尺寸为图像的尺寸。MaxPooling2D池化层是将图像进行压缩,只保留每个池化块中的最大值。

model = tf.keras.models.Sequential([
  tf.keras.layers.Conv2D(64, (3,3), activation='relu', input_shape=(28, 28, 1)),
  tf.keras.layers.MaxPooling2D(2, 2),
  tf.keras.layers.Conv2D(64, (3,3), activation='relu'),
  tf.keras.layers.MaxPooling2D(2,2),
  tf.keras.layers.Flatten(),
  tf.keras.layers.Dense(128, activation='relu'),
  tf.keras.layers.Dense(10, activation='softmax')
])
卷积、池化

通过下图可以看到模型每层的参数,第一层的卷积层输入的是(28,28,1),但是输出的(26,26,1)。这是因为卷积时没有进行边缘填充,所有左右上下更少了一个像素。池化层是(2,2),所以图像尺寸变为原来的一半。


模型参数
3.使用卷积神经网络处理真实图片

真实图像相比数据集更加复杂,且像素更多,因此构建一个5层的卷积网络,初始输入尺寸为(300,300,3)。在这个数据集中,图像为二分类问题,所以最后输出层只需要一个神经元,输出的是0-1的之间的数,表示概率。概率越接近1,表示图像为人的概率越大,概率越接近0,表示图像为马的概率越大。输出层的激活函数为sigmoid

model = tf.keras.models.Sequential([
    tf.keras.layers.Conv2D(16, (3,3), activation='relu', input_shape=(300, 300, 3)),
    tf.keras.layers.MaxPooling2D(2, 2),
    
    tf.keras.layers.Conv2D(32, (3,3), activation='relu'),
    tf.keras.layers.MaxPooling2D(2,2),
    
    tf.keras.layers.Conv2D(64, (3,3), activation='relu'),
    tf.keras.layers.MaxPooling2D(2,2),
    
    tf.keras.layers.Conv2D(64, (3,3), activation='relu'),
    tf.keras.layers.MaxPooling2D(2,2),
    
    tf.keras.layers.Conv2D(64, (3,3), activation='relu'),
    tf.keras.layers.MaxPooling2D(2,2),
   
    tf.keras.layers.Flatten(),
    tf.keras.layers.Dense(512, activation='relu'),
    tf.keras.layers.Dense(1, activation='sigmoid')
])

使用keras中的图像处理类来处理图像,ImageDataGenerator是keras.preprocessing.image模块中的图片生成器,可以每一次给模型“喂”一个batch_size大小的样本数据,同时也可以在每一个批次中对这batch_size个样本数据进行增强,扩充数据集大小,增强模型的泛化能力。比如进行旋转,变形,归一化等等。
因为神经网络的输入尺寸定义为(300,300,3),所以这里需要将图像的尺寸定义为(300,300)。每个batch定义为128张图片。因为上面神经网络采用的损失函数是binary_crossentropy,所以我们需要二分类的标签。

from tensorflow.keras.preprocessing.image import ImageDataGenerator

train_datagen = ImageDataGenerator(rescale=1/255)

train_generator = train_datagen.flow_from_directory(
        '/tmp/horse-or-human/', 
        target_size=(300, 300), 
        batch_size=128,
        class_mode='binary')

使用fit_generator训练模型。verbose:日志显示。verbose = 0 为不在标准输出流输出日志信息。verbose = 1 为输出进度条记录。verbose = 2 为每个epoch输出一行记录。注意: 默认为 1。

history = model.fit_generator(
      train_generator,
      steps_per_epoch=8,  
      epochs=15,
      verbose=1)

最后使用model.predict来对需要检测的图片进行测试。对于输出的概率使用0.5最为分解数值,大于0.5判断为人,小于0.5判断为马。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 216,496评论 6 501
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 92,407评论 3 392
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 162,632评论 0 353
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,180评论 1 292
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,198评论 6 388
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,165评论 1 299
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,052评论 3 418
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,910评论 0 274
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,324评论 1 310
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,542评论 2 332
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,711评论 1 348
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,424评论 5 343
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,017评论 3 326
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,668评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,823评论 1 269
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 47,722评论 2 368
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,611评论 2 353