# 第8周：人工智能应用（一）- 图像分类CNN - 讲义

## 教学目标

| 目标 | 内容 |
|-----|------|
| 知识目标 | 理解CNN卷积神经网络原理、图像分类流程 |
| 能力目标 | 能够部署图像分类模型到ESP32 |
| 情感目标 | 建立"机器是怎么学习的"的深层认识 |

---

## 课程导入（10分钟）

### 8.1 开场Demo设计

**Demo名称：手写数字识别**

**演示流程：**
1. 在纸上写一个数字（如"7"）
2. ESP32-CAM拍摄纸张
3. 屏幕上显示识别结果："识别结果：7"

**引导语：**
> "同学们，刚才机器'看懂'了我们写的数字——这就是卷积神经网络（CNN）的作用。今天学完，你们也能做出来。"

---

## 原理讲解（40分钟）

### 8.2 传统图像处理 vs 深度学习

#### 8.2.1 传统方法的问题

```
传统图像处理流程：
┌─────────────────────────────────────────────────────────────┐
│  原始图像 → 预处理 → 特征提取 → 分类器 → 结果              │
└─────────────────────────────────────────────────────────────┘

问题：
• 特征提取需要人工设计（如SIFT、HOG）
• 换一个问题就要重新设计特征
• 泛化能力差
```

#### 8.2.2 深度学习的方法

```
深度学习流程：
┌─────────────────────────────────────────────────────────────┐
│  原始图像 → 神经网络 → 特征学习 → 分类 → 结果               │
└─────────────────────────────────────────────────────────────┘

优势：
• 特征自动学习，不需要人工设计
• 端到端学习
• 泛化能力强
```

---

### 8.3 卷积神经网络 (CNN)

#### 8.3.1 CNN核心概念

```
CNN = Convolutional Neural Network
      卷积神经网络

核心结构：
┌─────────────────────────────────────────────────────────────┐
│                                                             │
│  输入层 → 卷积层 → 池化层 → 卷积层 → 池化层 → 全连接层 → 输出 │
│                                                             │
└─────────────────────────────────────────────────────────────┘

卷积层：提取图像特征
池化层：压缩特征，减少计算量
全连接层：整合特征，进行分类
```

#### 8.3.2 卷积操作

```
卷积 = 用滤波器（卷积核）在图像上滑动

        输入图像 (5×5)          卷积核 (3×3)         输出特征图
        ┌─────────┐
        │ 1 2 3 1 2│
        │ 2 1 2 1 3│       ┌───────┐         ┌───────┐
        │ 3 2 1 2 1│   ⊗   │ 1 0 1 │    =    │ 特征1 │
        │ 1 2 1 3 2│       │ 0 1 0 │         │ 特征2 │
        │ 2 1 2 1 2│       │ 1 0 1 │         │ ...   │
        └─────────┘       └───────┘         └───────┘

卷积核在图像上滑动，计算局部区域的加权和
不同的卷积核提取不同的特征
```

#### 8.3.3 常见卷积核

| 卷积核 | 效果 | 用途 |
|--------|------|------|
| 边缘检测 | 提取轮廓 | 预处理 |
| 锐化 | 增强细节 | 增强 |
| 模糊 | 平滑图像 | 去噪 |
| 45度检测 | 提取斜边 | 特征 |

---

### 8.4 池化层

#### 8.4.1 最大池化

```
池化 = 降采样，减少特征图尺寸

最大池化 (2×2)：
┌─────────────────┐
│ 1  5  3  2     │
│ 4  2  1  6     │  →  2×2分块 → 每块取最大值
│ 3  8  2  1     │     ┌───────┐
│ 1  2  4  3     │     │ 5  6  │
└─────────────────┘     │ 8  4  │
                        └───────┘

效果：压缩数据，保留显著特征
```

---

### 8.5 LeNet-5 经典网络

#### 8.5.1 网络结构

```
LeNet-5 (1998年，用于手写数字识别)：

输入(32×32) → C1(6@28×28) → S2(6@14×14) → C3(16@10×10) → S4(16@5×5) → C5(120) → F6(84) → 输出(10)

层类型：
• C: 卷积层 (Convolutional)
• S: 池化层 (Subsampling)
• F: 全连接层 (Fully Connected)
```

#### 8.5.2 手写数字识别流程

```
输入：手写数字图像 (28×28灰度)
        ↓
卷积层1 + 池化层1 → 提取边缘特征
        ↓
卷积层2 + 池化层2 → 提取纹理特征
        ↓
全连接层 → 整合特征
        ↓
输出层(10) → 概率分布 [0.01, 0.02, 0.85, ...]
                    数字:   0    1    2  ...
```

---

### 8.6 TensorFlow Lite Micro

#### 8.6.1 什么是TFLite Micro

```
TensorFlow Lite Micro = TensorFlow的嵌入式版本
• 专门为微控制器优化
• 支持ESP32、Arduino等
• 模型量化，减小体积
```

#### 8.6.2 模型量化

```
量化 = 将32位浮点数转换为8位整数

量化前：float32 (4字节)  →  量化后：int8 (1字节)
模型大小：1MB  →  256KB

精度损失：<1%（可接受）
```

---

## 实验操作（40分钟）

### 8.7 实验：图像分类模型部署

#### 实验目的
- 学习使用TensorFlow Lite Micro
- 在ESP32上部署图像分类模型
- 实现手写数字识别

#### 实验器材
- ESP32-CAM × 1
- 纸和笔（写数字用）
- FTDI编程器

#### 实验步骤

**1. 训练模型（使用预训练模型）**
```
MNIST手写数字识别模型已经训练好
直接下载使用：ESP32-compatible model
```

**2. Arduino库安装**
```
1. Arduino IDE → 项目 → 加载库 → 添加.zip库
2. 选择下载的TFLite Micro库
3. 安装TensorFlowLite_ESP32
```

**3. 编写代码**
```cpp
#include <TensorFlowLite_ESP32.h>
#include "model.h"  // 预训练模型

// 图像预处理
void preprocess(camera_fb_t *fb) {
    // 1. 转为灰度
    // 2. 缩放到28×28
    // 3. 归一化到0-1
}

// 推理
void predict() {
    // 获取图像
    camera_fb_t *fb = esp_camera_fb_get();
    
    // 预处理
    preprocess(fb);
    
    // 模型推理
    float output[10];
    inference->Invoke(output);
    
    // 找最大概率
    int maxIndex = 0;
    float maxProb = output[0];
    for (int i = 1; i < 10; i++) {
        if (output[i] > maxProb) {
            maxProb = output[i];
            maxIndex = i;
        }
    }
    
    Serial.printf("识别结果: %d (置信度: %.2f)\n", maxIndex, maxProb);
    
    esp_camera_fb_return(fb);
}
```

---

## 知识总结

### 8.8 CNN学习流程

```
1. 数据准备 → 收集训练数据（手写数字图片）
        ↓
2. 数据预处理 → 灰度化、归一化、增强
        ↓
3. 构建网络 → 设计CNN结构
        ↓
4. 训练 → 反向传播优化参数
        ↓
5. 评估 → 测试准确率
        ↓
6. 量化 → 转换为int8，减小体积
        ↓
7. 部署 → 烧录到ESP32
```

---

## 课后作业

1. **理论题**：解释卷积和池化的作用
2. **实践题**：完成图像分类模型部署实验
3. **思考题**：为什么CNN比全连接网络更适合图像？

---

## 延伸阅读

- 《深度学习入门：基于Python的理论与实现》
- TensorFlow Lite文档：https://www.tensorflow.org/lite/microcontrollers
