Pytorch-以数字识别更好地入门深度学习

目录

一、数据介绍

二、下载数据 

三、可视化数据

四、模型构建

五、模型训练

六、模型预测


一、数据介绍

MNIST数据集是深度学习入门的经典案例,因为它具有以下优点:

1. 数据量小,计算速度快。MNIST数据集包含60000个训练样本和10000个测试样本,每张图像的大小为28x28像素,这样的数据量非常适合在GPU上进行并行计算。

2. 标签简单,易于理解。MNIST数据集的标签只有0-9这10个数字,相比其他图像分类数据集如CIFAR-10等更加简单易懂。

3. 数据集已标准化。MNIST数据集中的图像已经被归一化到0-1之间,这使得模型可以更快地收敛并提高准确率。

4. 适合初学者练习。MNIST数据集是深度学习入门的最佳选择之一,因为它既不需要复杂的数据预处理,也不需要大量的计算资源,可以帮助初学者快速上手深度学习。

综上所述,MNIST数据集是深度学习入门的经典案例,它具有数据量小、计算速度快、标签简单、数据集已标准化、适合初学者练习等优点,因此被广泛应用于深度学习的教学和实践中。

手写数字识别技术的应用非常广泛,例如在金融、保险、医疗、教育等领域中,都有很多应用场景。手写数字识别技术可以帮助人们更方便地进行数字化处理,提高工作效率和准确性。此外,手写数字识别技术还可以用于机器人控制、智能家居等方面  。

使用torch.datasets.MNIST下载到指定目录下:./data,当download=True时,如果已经下载了不会再重复下载,同train选择下载训练数据还是测试数据

官方提供的类:

class MNIST(root: str,train: bool = True,transform: ((...) -> Any) | None = None,target_transform: ((...) -> Any) | None = None,download: bool = False
)
Args:root (string): Root directory of dataset where MNIST/raw/train-images-idx3-ubyteand MNIST/raw/t10k-images-idx3-ubyte exist.train (bool, optional): If True, creates dataset from train-images-idx3-ubyte,otherwise from t10k-images-idx3-ubyte.download (bool, optional): If True, downloads the dataset from the internet andputs it in root directory. If dataset is already downloaded, it is not downloaded again.transform (callable, optional): A function/transform that takes in an PIL imageand returns a transformed version. E.g, transforms.RandomCroptarget_transform (callable, optional): A function/transform that takes in thetarget and transforms it.

二、下载数据 

# 导入数据集
# 训练集
import torch
from torchvision import datasets,transforms
from torch.utils.data import Dataset
train_loader = torch.utils.data.DataLoader(datasets.MNIST(root="./data",train=True,download=True,transform=transforms.Compose([transforms.ToTensor(),transforms.Normalize((0.1307,),(0.3081,))])),batch_size=64,shuffle=True)# 测试集
test_loader = torch.utils.data.DataLoader(datasets.MNIST("./data",train=False,transform=transforms.Compose([transforms.ToTensor(),transforms.Normalize((0.1307,),(0.3081,))])),batch_size=64,shuffle=True
)

pytorch也提供了自定义数据的方法,根据自己数据进行处理

使用PyTorch提供的Dataset和DataLoader类来定制自己的数据集。如果想个性化自己的数据集或者数据传递方式,也可以自己重写子类。

以下是一个简单的例子,展示如何创建一个自定义的数据集并将其传递给模型进行训练:

import torch
from torch.utils.data import Dataset, DataLoaderclass MyDataset(Dataset):def __init__(self, data, labels):self.data = dataself.labels = labelsdef __len__(self):return len(self.data)def __getitem__(self, index):x = self.data[index]y = self.labels[index]return x, ydata = torch.randn(100, 3, 32, 32)
labels = torch.randint(0, 10, (100,))my_dataset = MyDataset(data, labels)
my_dataloader = DataLoader(my_dataset, batch_size=4, shuffle=True)

详细完整流程可参考: Pytorch快速搭建并训练CNN模型?

三、可视化数据

mport matplotlib.pyplot as plt
import numpy as np
import torchvision
def imshow(img):img = img / 2 + 0.5 # 逆归一化npimg = img.numpy()plt.imshow(np.transpose(npimg,(1,2,0)))plt.title("Label")plt.show()# 得到batch中的数据
dataiter = iter(train_loader)
images,labels = next(dataiter)
# 展示图片
imshow(torchvision.utils.make_grid(images))

四、模型构建

定义模型类并继承nn.Module基类

# 构建模型
import torch.nn as nn
import torch
import torch.nn.functional as F
class MyNet(nn.Module):def __init__(self):super(MyNet,self).__init__()# 输入图像为单通道,输出为六通道,卷积核大小为5×5self.conv1 = nn.Conv2d(1,6,5)self.conv2 = nn.Conv2d(6,16,5)# 将16×4×4的Tensor转换为一个120维的Tensor,因为后面需要通过全连接层self.fc1 = nn.Linear(16*4*4,120)self.fc2 = nn.Linear(120,84)self.fc3 = nn.Linear(84,10)def forward(self,x):# 在(2,2)的窗口上进行池化x = F.max_pool2d(F.relu(self.conv1(x)),2)x = F.max_pool2d(F.relu(self.conv2(x)),2)# 将维度转换成以batch为第一维,剩余维数相乘为第二维x = x.view(-1,self.num_flat_features(x))x = F.relu(self.fc1(x))x = F.relu(self.fc2(x))x = self.fc3(x)return xdef num_flat_features(self,x):size = x.size()[1:]num_features = 1for s in size:num_features *= sreturn num_featuresnet = MyNet()
print(net)

输出: 

MyNet((conv1): Conv2d(1, 6, kernel_size=(5, 5), stride=(1, 1))(conv2): Conv2d(6, 16, kernel_size=(5, 5), stride=(1, 1))(fc1): Linear(in_features=256, out_features=120, bias=True)(fc2): Linear(in_features=120, out_features=84, bias=True)(fc3): Linear(in_features=84, out_features=10, bias=True)
)

简单的前向传播

# 前向传播
print(len(images))
image = images[:2]
label = labels[:2]
print(image.shape)
print(image.size())
print(label)
out = net(image)
print(out)

输出: 

16
torch.Size([2, 1, 28, 28])
torch.Size([2, 1, 28, 28])
tensor([6, 0])
tensor([[ 1.5441e+00, -1.2524e+00,  5.7165e-01, -3.6299e+00,  3.4144e+00,2.7756e+00,  1.1974e+01, -6.6951e+00, -1.2850e+00, -3.5383e+00],[ 6.7947e+00, -7.1824e+00,  8.8787e-01, -5.2218e-01, -4.1045e+00,4.6080e-01, -1.9258e+00,  1.8958e-01, -7.7214e-01, -6.3265e-03]],grad_fn=<AddmmBackward0>)

计算损失:

# 计算损失
# 因为是多分类,所有采用CrossEntropyLoss函数,二分类用BCELoss
image = images[:2]
label = labels[:2]
out = net(image)
criterion = nn.CrossEntropyLoss()
loss = criterion(out,label)
print(loss)

输出:

tensor(2.2938, grad_fn=<NllLossBackward0>)

五、模型训练

# 开始训练
model = MyNet()
# device = torch.device("cuda:0")
# model = model.to(device)
import torch.optim as optim
optimizer = optim.SGD(model.parameters(),lr=0.01) # lr表示学习率
criterion = nn.CrossEntropyLoss()
def train(epoch):# 设置为训练模式:某些层的行为会发生变化(dropout和batchnorm:会根据当前批次的数据计算均值和方差,加速模型的泛化能力)model.train()running_loss = 0.0for i,data in enumerate(train_loader):# 得到输入和标签inputs,labels = data# 消除梯度optimizer.zero_grad()# 前向传播、计算损失、反向传播、更新参数outputs = model(inputs)loss = criterion(outputs,labels)loss.backward()optimizer.step()# 打印日志running_loss += loss.item()if i % 100 == 0:print("[%d,%5d] loss: %.3f"%(epoch+1,i+1,running_loss/100))running_loss = 0train(10)

输出:

[11,    1] loss: 0.023
[11,  101] loss: 2.302
[11,  201] loss: 2.294
[11,  301] loss: 2.278
[11,  401] loss: 2.231
[11,  501] loss: 1.931
[11,  601] loss: 0.947
[11,  701] loss: 0.601
[11,  801] loss: 0.466
[11,  901] loss: 0.399

六、模型预测

# 模型预测结果
correct = 0
total = 0
with torch.no_grad():for data in test_loader:images,labels = dataoutputs = model(images)# 最大的数值及最大值对应的索引value,predicted = torch.max(outputs.data,1)total += labels.size(0)# 对bool型的张量进行求和操作,得到所有预测正确的样本数,采用item将整数类型的张量转换为python中的整型对象correct += (predicted == labels).sum().item()print("predicted:{}".format(predicted[:10].tolist()))print("label:{}".format(labels[:10].tolist()))print("Accuracy of the network on the 10 test images: %d %%"% (100*correct/total))imshow(torchvision.utils.make_grid(images[:10],nrow=len(images[:10])))

输出:

predicted:[1, 0, 7, 6, 5, 2, 4, 3, 2, 6]
label:[1, 0, 7, 6, 5, 2, 4, 8, 2, 6]
Accuracy of the network on the 10 test images: 91 %

对应类别的准确率:

class_correct = list(0. for i in range(10))
class_total = list(0. for i in range(10))
classes = [i for i in range(10)]with torch.no_grad():# model.eval()for data in test_loader:images,labels = dataoutputs = model(images)value,predicted = torch.max(outputs,1)c = (predicted == labels).squeeze()# 对所有labels逐个进行判断for i in range(len(labels)):label = labels[i]class_correct[label] += c[i].item()class_total[label] += 1print("class_correct:{}".format(class_correct))print("class_total:{}".format(class_total))# 每个类别的指标
for i in range(10):print('Accuracy of -> class %d : %2d %%'%(classes[i],100*class_correct[i]/class_total[i]))

输出:

class_correct:[958.0, 1119.0, 948.0, 938.0, 901.0, 682.0, 913.0, 918.0, 748.0, 902.0]
class_total:[980.0, 1135.0, 1032.0, 1010.0, 982.0, 892.0, 958.0, 1028.0, 974.0, 1009.0]
Accuracy of -> class 0 : 97 %
Accuracy of -> class 1 : 98 %
Accuracy of -> class 2 : 91 %
Accuracy of -> class 3 : 92 %
Accuracy of -> class 4 : 91 %
Accuracy of -> class 5 : 76 %
Accuracy of -> class 6 : 95 %
Accuracy of -> class 7 : 89 %
Accuracy of -> class 8 : 76 %
Accuracy of -> class 9 : 89 %

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/93672.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【OpenCV入门】第六部分——腐蚀与膨胀

文章结构 腐蚀膨胀开运算闭运算形态学方法梯度运算顶帽运算黑帽运算 腐蚀 腐蚀操作可以让图像沿着自己的边界向内收缩。OpenCV通过”核“来实现收缩计算。“核”在形态学中可以理解为”由n个像素组成的像素块“&#xff0c;像素块包含一个核心&#xff08;通常在中央位置&…

HTTP介绍:一文了解什么是HTTP

前言&#xff1a; 在当今数字时代&#xff0c;互联网已经成为人们生活中不可或缺的一部分。无论是浏览网页、发送电子邮件还是在线购物&#xff0c;我们都离不开超文本传输协议&#xff08;HTTP&#xff09;。HTTP作为一种通信协议&#xff0c;扮演着连接客户端和服务器的重要角…

excel绘制直方图

Excel 2016直方图使用指南 excel绘制各种曲线十分方便&#xff0c;可以通过代码将计算的数据输出到excel里面&#xff0c;然后通过excel的插入标签&#xff0c;绘制各种需要的曲线。 对于直方图&#xff0c;横坐标是分布区间&#xff0c;纵坐标是这个区间内数值的频数&#x…

Python项目编译与部署(1):模块与包的概念与关系

当实际构建1个 Python 项目时&#xff0c;模块与包是我们面临的基础概念。 1、模块、包的概念 Python中的模块(Module), 就是一个单独的.py文件&#xff0c;其中包含变量定义&#xff0c;函数定义、类定义、以及其它可执行语句。模块是一个独立的代码单元&#xff0c;可以用解…

海康机器人工业相机 Win10+Qt+Cmake 开发环境搭建

文章目录 一. Qt搭建海康机器人工业相机开发环境 一. Qt搭建海康机器人工业相机开发环境 参考这个链接安装好MVS客户端 Qt新建一个c项目 cmakeList中添加海康机器人的库&#xff0c;如下&#xff1a; cmake_minimum_required(VERSION 3.5)project(HIKRobotCameraTest LANG…

无涯教程-JavaScript - NEGBINOMDIST函数

NEGBINOMDIST函数取代了Excel 2010中的NEGBINOM.DIST函数。 描述 该函数返回负二项式分布。 NEGBINOMDIST返回在第number_s次成功之前出现number_f次失败的概率,而成功的恒定概率是概率_s。 该函数与二项式分布相似,不同之处在于成功次数是固定的,而试验次数是可变的。像二项…

excel怎么设置任意选一个单元格纵横竖横都有颜色

有时excel表格内容过多的时候&#xff0c;我们通过excel设置任意选一个单元格纵横&#xff0c;竖横背景颜色&#xff0c;这样会更加具有辨识度。设置方式截图如下 设置成功后&#xff0c;预览的效果图

【STM32】SPI初步使用 读写FLASH W25Q64

硬件连接 (1) SS( Slave Select)&#xff1a;从设备选择信号线&#xff0c;常称为片选信号线&#xff0c;每个从设备都有独立的这一条 NSS 信号线&#xff0c;当主机要选择从设备时&#xff0c;把该从设备的 NSS 信号线设置为低电平&#xff0c;该从设备即被选中&#xff0c;即…

ChatGPT⼊门到精通(4):ChatGPT 为何⽜逼

⼀、通⽤型AI 在我们原始的幻想⾥&#xff0c;AI是基于对海量数据的学习&#xff0c;锻炼出⼀个⽆所不知⽆所不能的模 型&#xff0c;并借助计算机的优势&#xff08;计算速度、并发可能&#xff09;等碾压⼈类。 但我们⽬前的AI&#xff0c;不管是AlphaGo还是图像识别算法&am…

【Axure高保真原型】中继器网格图片拖动摆放

今天和大家分享中继器网格图片拖动摆放的原型模板&#xff0c;我们可以通过鼠标拖动来移动图片&#xff0c;拖动过程其他图标会根据图片拖动自动排列&#xff0c;松开鼠标是图片停放在指定位置&#xff0c;其他图标自动排列。那这个模板是用中继器制作的&#xff0c;所以使用也…

Android Native Code开发学习(二)JNI互相传参返回调用

Android Native Code开发学习&#xff08;二&#xff09; 本教程为native code学习笔记&#xff0c;希望能够帮到有需要的人 我的电脑系统为ubuntu 22.04&#xff0c;当然windows也是可以的&#xff0c;区别不大 一、native code介绍 native code就是在android项目中混合C或…

XXE漏洞利用技巧(由简入深)-----portswigger(XXE部分WP)

什么是XXE XXE&#xff08;XML External Entity&#xff1a;xml外部实体注入&#xff09;&#xff0c;它出现在使用XML解析器的应用程序中。XXE攻击利用了XML解析器的功能&#xff0c;允许应用程序从外部实体引用加载数据。攻击者可以通过构造恶意的XML实体引用来读取本地文件…