3. 多层感知机(MLP)

多层感知机(MLP) 学习卡片

任务说明

本案例实现一个包含一个隐藏层的多层感知机(MLP),在MNIST手写数字数据集上完成分类任务。模型输入为28×28=784维像素向量,隐藏层128个神经元,输出层10个类别。训练完成后,在测试集上评估模型准确率。

实现代码

import torch
import torch.nn as nn
import torch.optim as optim
from torch.utils.data import DataLoader
from torchvision import datasets, transforms

# 1. 数据准备
transform = transforms.Compose([
    transforms.ToTensor(),
    transforms.Normalize((0.1307,), (0.3081,))
])

train_dataset = datasets.MNIST(root='./data', train=True, download=True, transform=transform)
test_dataset = datasets.MNIST(root='./data', train=False, download=True, transform=transform)

train_loader = DataLoader(train_dataset, batch_size=64, shuffle=True)
test_loader = DataLoader(test_dataset, batch_size=256, shuffle=False)

# 2. 定义MLP模型
class MLP(nn.Module):
    def __init__(self, input_dim=784, hidden_dim=128, output_dim=10):
        super(MLP, self).__init__()
        self.fc1 = nn.Linear(input_dim, hidden_dim)
        self.relu = nn.ReLU()
        self.fc2 = nn.Linear(hidden_dim, output_dim)

    def forward(self, x):
        x = x.view(x.size(0), -1)  # 展平为 [batch, 784]
        x = self.fc1(x)
        x = self.relu(x)
        x = self.fc2(x)
        return x

# 3. 初始化模型、损失函数、优化器
device = torch.device('cuda' if torch.cuda.is_available() else 'cpu')
model = MLP().to(device)
criterion = nn.CrossEntropyLoss()
optimizer = optim.Adam(model.parameters(), lr=0.001)

# 4. 训练
epochs = 5
for epoch in range(epochs):
    model.train()
    running_loss = 0.0
    for images, labels in train_loader:
        images, labels = images.to(device), labels.to(device)
        optimizer.zero_grad()
        outputs = model(images)
        loss = criterion(outputs, labels)
        loss.backward()
        optimizer.step()
        running_loss += loss.item() * images.size(0)
    epoch_loss = running_loss / len(train_loader.dataset)
    print(f'Epoch [{epoch+1}/{epochs}], Loss: {epoch_loss:.4f}')

# 5. 测试
model.eval()
correct = 0
total = 0
with torch.no_grad():
    for images, labels in test_loader:
        images, labels = images.to(device), labels.to(device)
        outputs = model(images)
        _, predicted = torch.max(outputs.data, 1)
        total += labels.size(0)
        correct += (predicted == labels).sum().item()

accuracy = 100.0 * correct / total
print(f'Test Accuracy: {accuracy:.2f}%')

落地方式

运行前需安装依赖:pip install torch torchvision。首次运行会自动下载MNIST数据集至./data目录。直接执行上述脚本即可完成训练与测试。

验证方法

观察训练过程中每个epoch的loss值是否逐步下降。训练结束后,程序输出测试集准确率。判定标准:测试准确率应达到97%以上(该结果由MLP在MNIST上的典型性能决定,实际值以运行为准)。

MLP训练与验证流程 MNIST数据集 60000训练/10000测试 预处理 ToTensor + Normalize MLP模型 输入784 → 隐藏128 ReLU → 输出10 训练循环 CrossEntropyLoss Adam优化器 反向传播更新权重 测试评估 计算准确率 输出结果 测试准确率 数据维度流转 输入图像: [64, 1, 28, 28] 展平后: [64, 784] 隐藏层输出: [64, 128] → ReLU 最终输出: [64, 10] → 预测类别

判定标准

训练过程中loss单调下降且最终测试准确率≥97%,即可判定案例实现成功。若准确率偏低,可检查数据预处理是否正确、增加训练轮数或调整学习率。