MLP和CNN在图片识别中的对比——基于猫狗分类项目的实战分析

一、引言

卷积神经网络(Convolutional Neural Network,CNN)在图像处理领域的强大性能早已是学界与工业界公认的事实。猫狗分类任务场景简单、数据易获取,同时又能涵盖图像分类的核心环节,非常适合作为第一个CNN的实践项目。

二、实验环境与实现流程

为确保实验可复现且结果清晰,本节将详细介绍项目的运行环境、核心实现步骤,并对关键代码进行逐块注释,帮助理解每一步的设计逻辑。

2.1 实验环境说明

本项目基于 Google Colab 平台运行,无需本地配置复杂环境,核心依赖如下:

  • 深度学习框架:TensorFlow 2.x(Colab 默认预装,含 Keras 高层 API)
  • 硬件加速:Colab 免费版提供的 GPU(通常为 NVIDIA T4,支持 CUDA 加速)
  • 数据处理与可视化库:Matplotlib(内置,用于绘制训练曲线)
  • 数据集:Google 提供的 cats_and_dogs_filtered 轻量级数据集(含 2000 张训练图、1000 张验证图,仅含 “猫 / 狗” 两类,适合快速验证模型)

2.2 完整实现流程与代码注释

实验流程遵循 “环境检查→数据准备→模型构建→模型训练→结果可视化” 的经典深度学习链路,每一步代码均附带详细注释,明确设计目的。

步骤 1:环境初始化与 GPU 检查

首先导入核心库,并确认 GPU 是否启用 ——GPU 能大幅加速卷积、矩阵运算等耗时操作,是训练 CNN 的关键。

# 导入必要的库:涵盖模型构建、数据处理、可视化全流程
import tensorflow as tf  # 深度学习核心框架
from tensorflow.keras import layers, models  # Keras 层与模型API
from tensorflow.keras.preprocessing.image import ImageDataGenerator  # 图像数据生成器(含增强功能)
from tensorflow.keras.utils import plot_model  # 可选:绘制模型结构图(需额外依赖)
import matplotlib.pyplot as plt  # 绘图库,用于展示训练曲线

# 检查GPU是否可用:Colab默认启用GPU,若显示空列表需手动切换(菜单栏→修改→笔记本设置→硬件加速器选GPU)
print("GPU 可用吗?", tf.config.list_physical_devices('GPU'))
# 预期输出:[PhysicalDevice(name='/physical_device:GPU:0', device_type='GPU')](表示GPU已启用)

步骤 2:数据集下载与解压

直接下载 Google 提供的公开数据集,无需手动上传,适合快速实验。

# 下载教学用数据集(Google 提供,无需验证,避免手动下载的繁琐)
# wget是Linux命令,用于从URL下载文件;-O指定保存文件名,--no-check-certificate跳过证书验证(避免网络问题)
!wget --no-check-certificate \
    https://storage.googleapis.com/mledu-datasets/cats_and_dogs_filtered.zip \
    -O cats_and_dogs_filtered.zip

# 解压数据集:-q表示“静默模式”(不输出解压日志),避免冗余信息
!unzip -q cats_and_dogs_filtered.zip

# 提示解压完成,便于确认流程进度
print("✅ 数据解压完成!")
# 解压后会生成“cats_and_dogs_filtered”文件夹,内含train(训练集)和validation(验证集)子文件夹

步骤 3:数据预处理与生成器创建

通过 ImageDataGenerator 实现图像归一化数据增强(仅用于训练集),并生成批量数据(避免一次性加载内存溢出)。

from tensorflow.keras.preprocessing.image import ImageDataGenerator  # 再次导入(确保代码块独立可运行)

# 1. 训练集数据增强:目的是扩大数据多样性,提升模型泛化能力(避免过拟合)
train_datagen = ImageDataGenerator(
    rescale=1./255,  # 核心预处理:将像素值从[0,255]归一化到[0,1],避免大数值导致梯度爆炸
    rotation_range=20,  # 随机旋转图像(0-20度),模拟不同拍摄角度
    width_shift_range=0.2,  # 随机水平偏移(最多占图像宽度的20%)
    height_shift_range=0.2,  # 随机垂直偏移(最多占图像高度的20%)
    horizontal_flip=True,  # 随机水平翻转(猫/狗左右翻转不影响类别,增加数据多样性)
    zoom_range=0.2  # 随机缩放(0.8-1.2倍),模拟不同拍摄距离
)

# 2. 验证集仅归一化:验证集需反映真实场景,不能做增强(否则评估结果不准确)
validation_datagen = ImageDataGenerator(rescale=1./255)

# 3. 训练集数据生成器:从文件夹读取图像,自动按类别标签(文件夹名)分类
train_generator = train_datagen.flow_from_directory(
    'cats_and_dogs_filtered/train',  # 训练集文件夹路径(内含cats/和dogs/两个子文件夹)
    target_size=(150, 150),  # 统一图像尺寸:将所有图像resize为150×150(模型输入需固定尺寸)
    batch_size=32,  # 每次训练批量大小:32是平衡速度与内存的常用值(Colab GPU可承载)
    class_mode='binary'  # 二分类任务(猫/狗),标签格式为二进制(0/1)
)

# 4. 验证集数据生成器:配置与训练集一致,仅无增强
validation_generator = validation_datagen.flow_from_directory(
    'cats_and_dogs_filtered/validation',  # 验证集文件夹路径
    target_size=(150, 150),
    batch_size=32,
    class_mode='binary'
)

# 打印数据集信息,确认数据加载正确
print("✅ 数据生成器创建成功!")
print("训练集图像数量:", train_generator.samples)        # 预期输出:2000(1000张猫+1000张狗)
print("验证集图像数量:", validation_generator.samples)    # 预期输出:1000(500张猫+500张狗)
print("类别索引:", train_generator.class_indices)         # 预期输出:{'cats': 0, 'dogs': 1}(文件夹名对应标签)

步骤 4:构建对比模型(MLP vs CNN)

为突出 CNN 在图像任务中的优势,同时构建 MLP 作为基线模型(Baseline),两者输入尺寸、全连接层参数尽量对齐,确保对比公平性。

4.1 构建 MLP 模型(多层感知机)

MLP 无空间特征提取能力,仅通过 “扁平化 + 全连接” 拟合数据,用于反衬 CNN 的优势。

from tensorflow.keras import models, layers  # 再次导入(确保代码块独立)

# 构建MLP模型:Sequential表示“序列模型”(层按顺序堆叠)
model_mlp = models.Sequential([
    # 输入层:将150×150×3的图像“扁平化”为1维向量(150*150*3=67500个特征)
    layers.Flatten(input_shape=(150, 150, 3)),
    # 全连接层1:512个神经元,ReLU激活函数(引入非线性,提升拟合能力)
    layers.Dense(512, activation='relu'),
    layers.Dropout(0.5),  # 随机丢弃50%神经元,防止过拟合(MLP易过拟合,需强正则化)
    # 全连接层2:128个神经元,进一步压缩特征
    layers.Dense(128, activation='relu'),
    layers.Dropout(0.5),  # 再次Dropout,增强泛化能力
    # 输出层:1个神经元,sigmoid激活函数(二分类任务,输出概率值[0,1])
    layers.Dense(1, activation='sigmoid')
])

# 编译模型:配置训练参数
model_mlp.compile(
    optimizer='adam',  # 优化器:Adam(自适应学习率,训练稳定)
    loss='binary_crossentropy',  # 
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值