计算机视觉入门 5)自定义卷积网络

系列文章目录

  1. 计算机视觉入门 1)卷积分类器
  2. 计算机视觉入门 2)卷积和ReLU
  3. 计算机视觉入门 3)最大池化
  4. 计算机视觉入门 4)滑动窗口
  5. 计算机视觉入门 5)自定义卷积网络
  6. 计算机视觉入门 6) 数据集增强(Data Augmentation)

提示:仅为个人学习笔记分享,若有错漏请各位老师同学指出,Thanks♪(・ω・)ノ



一、自定义卷积网络

从简单到精细

前几篇笔记介绍了卷积网络通过三个操作进行特征提取过滤检测压缩。一次特征提取只能从图像中提取相对简单的特征,例如简单的线条或对比度。这些特征对于解决大多数分类问题来说过于简单。相反,卷积网络会一遍又一遍地重复这个提取过程,使特征在网络内部深入传递时变得更加复杂和精细。
从图像中提取的特征,从简单到精细。

卷积块

它通过将图像通过一系列的卷积块来进行这个过程,从而实现这一点。
作为一系列块的提取过程。

这些卷积块是Conv2DMaxPool2D层的堆叠,如下所示:

一种提取块:卷积,ReLU,池化。

每个块代表一轮提取,通过组合这些块,卷积网络可以将产生的特征组合和重新组合。现代卷积网络的深层结构使得这种复杂的特征工程成为可能,从而大大提高它们在处理和解决任务上的性能。

二、【代码示例】构建一个简单的卷积网络

步骤1 - 加载数据

# 导入库
import os, warnings
import matplotlib.pyplot as plt
from matplotlib import gridspec

import numpy as np
import tensorflow as tf
from tensorflow.keras.preprocessing import image_dataset_from_directory

# 设置随机种子以保证可复现性
def set_seed(seed=31415):
    np.random.seed(seed)
    tf.random.set_seed(seed)
    os.environ['PYTHONHASHSEED'] = str(seed)
    os.environ['TF_DETERMINISTIC_OPS'] = '1'
set_seed()

# 设置Matplotlib默认值
plt.rc('figure', autolayout=True)
plt.rc('axes', labelweight='bold', labelsize='large',
       titleweight='bold', titlesize=18, titlepad=10)
plt.rc('image', cmap='magma')
warnings.filterwarnings("ignore") # 清理输出单元格

# 加载训练集和验证集
ds_train_ = image_dataset_from_directory(
    '../input/car-or-truck/train',
    labels='inferred',
    label_mode='binary',
    image_size=[128, 128],
    interpolation='nearest',
    batch_size=64,
    shuffle=True,
)
ds_valid_ = image_dataset_from_directory(
    '../input/car-or-truck/valid',
    labels='inferred',
    label_mode='binary',
    image_size=[128, 128],
    interpolation='nearest',
    batch_size=64,
    shuffle=False,
)

# 数据处理管道
def convert_to_float(image, label):
    image = tf.image.convert_image_dtype(image, dtype=tf.float32)
    return image, label

AUTOTUNE = tf.data.experimental.AUTOTUNE
ds_train = (
    ds_train_
    .map(convert_to_float)
    .cache()
    .prefetch(buffer_size=AUTOTUNE)
)
ds_valid = (
    ds_valid_
    .map(convert_to_float)
    .cache()
    .prefetch(buffer_size=AUTOTUNE)
)

步骤2 - 定义模型

下面是我们将使用的模型的图示:

卷积模型的图示。

现在我们来定义模型。注意我们的模型由三个 Conv2DMaxPool2D 层块组成,后面跟着一些 Dense 层。我们可以通过填写适当的参数,将这个图示基本上直接转化为一个 Keras Sequential 模型。

from tensorflow import keras
from tensorflow.keras import layers

model = keras.Sequential([

    # 第一个卷积块
    layers.Conv2D(filters=32, kernel_size=5, activation="relu", padding='same',
                  # 在第一层中提供输入维度
                  # [高度, 宽度, 颜色通道(RGB)]
                  input_shape=[128, 128, 3]),
    layers.MaxPool2D(),

    # 第二个卷积块
    layers.Conv2D(filters=64, kernel_size=3, activation="relu", padding='same'),
    layers.MaxPool2D(),

    # 第三个卷积块
    layers.Conv2D(filters=128, kernel_size=3, activation="relu", padding='same'),
    layers.MaxPool2D(),

    # 分类头部
    layers.Flatten(),
    layers.Dense(units=6, activation="relu"),
    layers.Dense(units=1, activation="sigmoid"),
])
model.summary()

这个代码定义了一个包含三个卷积块的模型,每个块都由一个 Conv2D 层和一个 MaxPool2D 层组成。最后的分类头部包括一个扁平化层(Flatten),两个密集连接层(Dense),用于输出预测结果。模型总共有大约50万个参数,它们将根据训练数据进行调整以进行有效的特征提取和分类。

输出模型Summary:
在这里插入图片描述
注意:这里每个块的过滤器数量都是逐块翻倍增加的:32、64、128。这是一种常见的模式。由于MaxPool2D层在每个块中降低了特征图的尺寸,因此我们可以逐块增加我们创建的特征图数量。

步骤3 - 训练模型

# 加入损失函数和准确率
model.compile(
    optimizer=tf.keras.optimizers.Adam(epsilon=0.01),
    loss='binary_crossentropy',
    metrics=['binary_accuracy']
)

#模型训练
history = model.fit(
    ds_train,
    validation_data=ds_valid,
    epochs=40,
    verbose=0,
)
import pandas as pd

#结果查看
history_frame = pd.DataFrame(history.history)
history_frame.loc[:, ['loss', 'val_loss']].plot()
history_frame.loc[:, ['binary_accuracy', 'val_binary_accuracy']].plot();

在这里插入图片描述
这个模型只有简单的3个卷积层,尽管如此,它仍然能够相当好地适应这个数据集。
见上图,蓝色曲线快速地变化,同时黄色曲线(验证集val)在10轮训练过程后就进入波动稳定的状态, 这表明模型容易过拟合,需要正则化处理。
后续可以添加更多的卷积层、或者Dropout层来进行正则化,继续改进这个模型。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值