pytorch MNIST数据集代码

本文详细介绍了如何使用PyTorch框架训练一个四层神经网络识别MNIST手写数字数据集。从数据预处理到模型构建,再到训练和评估,全程实战操作并附带代码解释。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

花了一上午的时间,用mnist数据集练习了pytorch训练神经网络,遇到问题就查资料,调节了很多小的bug,写有比较详细的注释

import numpy as np
import torch
from torchvision.datasets import mnist
import torchvision
from torch import nn
from torch.autograd import Variable
from torch.utils.data import DataLoader, TensorDataset
import torchvision.transforms as transforms

# 数据预处理,将28*28的变成784的格式大小
def data_tf(x):
    x = np.array(x, dtype="float32") / 255
    x = (x - 0.5) / 0.5
    x = x.reshape((-1))
    x = torch.from_numpy(x)
    return x

# 数据预处理,这里没有使用
transform = transforms.ToTensor()

#  载入数据,并使用transform=data_tf对数据惊醒类型和格式转换
train_set = mnist.MNIST("./data", train=True, download=True, transform=data_tf)
test_set = mnist.MNIST("./data", train=True, download=True, transform=data_tf)

# 使用数据迭代器,每一个batch_size=64
train_data = DataLoader(train_set, batch_size=64, shuffle=True)
test_data = DataLoader(test_set, batch_size=128, shuffle=False)

# 构建4层神经网络
net = nn.Sequential(
    nn.Linear(784, 400),
    nn.ReLU(),
    nn.Linear(400, 200),
    nn.ReLU(),
    nn.Linear(200, 100),
    nn.ReLU(),
    nn.Linear(100, 10)
)

# 损失函数使用交叉熵函数,采用随机梯度下降法,学习率为0.1
criterion = nn.CrossEntropyLoss()
optimizer = torch.optim.SGD(net.parameters(), 1e-1)

losses = []
acces = []
eval_losses = []
eval_acces =[]

for e in range(20):
    train_loss = 0
    train_acc = 0
    net.train()
    for im, label in train_data:
        im = Variable(im)
        lable = Variable(label)
        # 前向传播
        out = net(im)
        loss = criterion(out, label)
        # print(out.shape)
        # print(out)
        # print(out.max(1))

        # 反向传播
        optimizer.zero_grad()
        loss.backward()
        optimizer.step()

        # 记录误差
        train_loss = train_loss + loss.data

        # torch.max(0)和 torch.max(1)分别是找出tensor里每列/每行中最大的值,并返回索引(即为对应的预测数字)
        _, pred = out.max(1)
        # 预测正确的总数
        num_correct = (pred == label).sum().data
        # 计算正确率
        acc = float(num_correct) / im.shape[0]  # 注意要换成浮点数,否则整形相除,acc一直为0
        # 将每一个batch的正确率相加,便于后面计算每一个epoch的正确率
        train_acc = train_acc + acc
    # 计算这个epoch的损失和正确率
    losses.append(train_loss / len(train_data))
    acces.append(train_acc / len(train_data))

    eval_loss = 0
    eval_acc = 0
    net.eval()
    # 测试集上测试
    for im, label in test_data:
        im = Variable(im)
        label = Variable(label)
        out = net(im)
        loss = criterion(out, label)

        eval_loss += loss.data
        _, pred = out.max(1)
        num_correct = (pred == label).sum().data
        acc = float(num_correct) / im.shape[0]
        eval_acc += acc

    # 计算这一个epoch在测试集上的损失和正确率
    eval_losses.append(eval_loss / len(test_data))
    eval_acces.append(eval_acc / len(test_data))

    # 最后打印出这一个epoch上训练集的正确率和损失,以及测试机上的正确率和损失
    print("epoch :{}, Train Loss:{:.6f}, Train ACC:{:.6f}, Eval Loss: {:.6f}, Eval ACC: {:.6f}".
    format(e, train_loss / len(train_data), train_acc / len(train_data), eval_loss / len(test_data),
            eval_acc / len(test_data)))

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值