深度学习-第P1周——实现mnist手写数字识别

news/2024/4/29 10:21:47/文章来源:https://blog.csdn.net/qq_45735298/article/details/128198300

深度学习-第P1周——实现mnist手写数字识

  • 深度学习-第P1周——实现mnist手写数字识
    • 一、前言
    • 二、我的环境
    • 三、前期工作
      • 1、导入依赖项并设置GPU
      • 2、导入数据集
      • 3、数据可视化
    • 四、构建简单的CNN网络
    • 五、训练模型
      • 1、设置超参数
      • 2、编写训练函数
      • 3、编写测试函数
      • 4、正式训练
    • 六、结果可视化
    • 七、总结

深度学习-第P1周——实现mnist手写数字识

一、前言

  • 🍨 本文为🔗365天深度学习训练营 中的学习记录博客
  • 🍖 原作者:K同学啊

二、我的环境

  • 电脑系统:Windows 10
  • 语言环境:Python 3.8.5
  • 编译器:colab在线编译
  • 深度学习环境:Pytorch

三、前期工作

1、导入依赖项并设置GPU

所需库函数的介绍:

  • numpy是Python科学计算的基本包。
  • matplotlib 是在Python中常用的绘制图形的库。
  • PyTorch是一个开源的深度学习框架,提供了各种张量操作并通过自动求导可以自动进行梯度计算,方便构建各种动态神经网络
  • torchvision是pytorch的一个图形库,它服务于PyTorch深度学习框架的,主要用来构建计算机视觉模型
  • torch.device代表将torch.Tensor分配到的设备的对象,其包含一个设备类型('cpu’或’cuda’设备类型)和可选的设备的序号。如果设备序号不存在,则为当前设备

导入依赖项:

1.#导入所需要的库
import torch
import torch.nn as nn
import matplotlib.pyplot as plt
import torchvisiondevice = torch.device("cuda" if torch.cuda.is_available() else "cpu")device

在这里插入图片描述

2、导入数据集

使用dataset下载MNIST数据集,并划分训练集和测试集

使用dataloader加载数据,并设置好基本的batch_size

torchvision.datasets.MNIST详解

torchvision.datasets.MNIST是pytorch自带的一个数据库,我们可以通过代码在线下载数据,这里使用的是torchvision.datasets中的MNIST数据集

函数原型:

torchvision.datasets.MNIST(root, train = True, transform = None, download = False)

参数说明:

  • root(string): 数据地址
  • train(string): True = 训练集, False = 测试集
  • transform(callable, optional): 这里的参数选择一个你想要的数据转化函数,直接完成数据转化
  • download(bool, optional):如果为True,从互联网上下载数据集,并把数据集放在root目录下
2.#加载数据集,并划分训练集和测试集
train_ds = torchvision.datasets.MNIST('data',train = True,  transform = torchvision.transforms.ToTensor(), #将数据类型转化为Tensor类型download = True  )
test_ds = torchvision.datasets.MNIST('data',train = False,transform = torchvision.transforms.ToTensor(),download = True)

torch.utils.data.DataLoader详解

  • torch.utils.data.DataLoader是pytorch自带的一个数据加载器,结合了数据集和取样器,并且可以提供多个线程处理数据量
  • 在训练模型时使用到此函数,用来把训练数据分成多个小组,此函数每次抛出一组数据。直至把所有的数据都抛出。就是做一个数据的初始化。

torch.utils.data.DataLoader(dataset, batch_size, shuffle)

参数说明:

  • dataset: 加载的数据集
  • batch_size:每批加载的样本大小,默认为1
  • shuffle:如果为True,则打乱数据的顺序
  • 如下第一个函数就是将训练集生成迭代数据,每次迭代的数据为32个,shuffle为洗牌操作,即打乱顺序。
batch_size = 32
train_dl = torch.utils.data.DataLoader(train_ds, batch_size = batch_size, shuffle = True)
test_dl = torch.utils.data.DataLoader(test_ds, batch_size = batch_size)#取一个批次查看数据格式
#数据的shape为:[batch_size, channel, height, weight]
#其中batch_size是样本批次,channel, height, weight分别是图片的通道数,高度和宽度
#train_dl本质上是一个可迭代对象,可以使用iter()进行访问,采用iter(dataloader)返回的是一个迭代器,然后可以使用next()访问。
#也可以使用enumerate(dataloader)的形式访问。
imgs, labels = next(iter(train_dl)) #第一次使用next访问的是迭代器里的第一批数据,二次是第二批,以此类推img = imgs[0] #访问第一批数据里的第一个数据
print(imgs.shape, img.shape)

()

3、数据可视化

3.#数据可视化
import numpy as np#指定图片大小,图片大小为20宽,5高的绘图(单位为英寸)
plt.figure(figsize = (20, 5))
#enumerate() 函数用于将一个可遍历的数据对象(如列表、元组或字符串)组合为一个索引序列,同时列出数据和数据下标,一般用在 for 循环当中。
for i, imgs in enumerate(imgs[:20]): #维度缩减,把维度为1的去掉 如:[32, 1, 28,28]->[32, 28, 28]npimg = np.squeeze(imgs.numpy())#将整个figure分成2行10列,绘制第i + 1个子图plt.subplot(2, 10, i + 1)# imshow()函数格式为:#matplotlib.pyplot.imshow(X, cmap=None)#X: 要绘制的图像或数组。#cmap: 颜色图谱(colormap), 默认绘制为RGB(A)颜色空间。plt.imshow(npimg, cmap = plt.cm.binary)plt.axis('off')

在这里插入图片描述

四、构建简单的CNN网络

对于一般的CNN网络来说,都是由特征提取网络和分类网络构成,其中特征提取网络用于提取图片的特征,分类网络用于将图片进行分类。

  • nn.Conv2d为卷积层,用于提取图片的特征,传入参数为输入channel,输出channel,池化核大小
  • nn.MaxPool2d为池化层,进行下采样,用更高层的抽象表示图像特征,传入参数为池化核大小
  • nn.ReLU为激活函数,使模型可以拟合非线性数据
  • nn.Linear为全连接层,可以起到特征提取器的作用,最后一层的全连接层也可以认为是输出层,传入参数为输入特征数和输出特征数(输入特征数由特征提取网络计算得到,如果不会计算可以直接运行网络,报错中会提示输入特征数的大小,下方网络中第一个全连接层的输入特征数为1600)
  • nn.Sequential可以按构造顺序连接网络,在初始化阶段就设定好网络结构,不需要在前向传播中重新写一遍

下方代码各函数参数详解:
nn.Conv2d(in_channels,out_channels,kernel_size,stride,padding) 二维卷积

  • in_channels: 输入张量的channels数
  • out_channels:期望输出张量的channels数
  • kernel_size:卷积核的大小
  • stride:步长,即卷积核在图像窗口上每次平移的间隔
  • padding:图像的填充数

nn.MaxPool2d(kernel_size)

  • kernel_size: 最大池化的窗口大小

nn.Linear(in_features,out_features,bias = Ture)

  • in_features:输入的神经元个数
  • out_features:输出的神经元个数
  • bias:是否包含偏置
#二、构建简单的CNN网络
# 创建并设置卷积神经网络
# 卷积层:通过卷积操作对输入图像进行降维和特征抽取
# 池化层:是一种非线性形式的下采样。主要用于特征降维,压缩数据和参数的数量,减小过拟合,同时提高模型的鲁棒性。
# 全连接层:在经过几个卷积和池化层之后,神经网络中的高级推理通过全连接层来完成。
import torch.nn.functional as F
num_classes = 10
class Model(nn.Module):def __init__(self):super().__init__()#特征提取网络self.conv1 = nn.Conv2d(1, 32, kernel_size = 3) # 第一层卷积,卷积核大小为3*3self.pool1 = nn.MaxPool2d(2)            #设置池化层,池化核大小为2*2  self.conv2 = nn.Conv2d(32, 64, kernel_size = 3) #第二层卷积,卷积核大小为3*3self.pool2 = nn.MaxPool2d(2)#分类网络self.fc1 = nn.Linear(1600, 64)self.fc2 = nn.Linear(64, num_classes)#前向传播def forward(self, x):x = self.pool1(F.relu(self.conv1(x)))x = self.pool2(F.relu(self.conv2(x)))x = torch.flatten(x, start_dim = 1) #Flatten层,连接卷积层与全连接层x = F.relu(self.fc1(x))x = self.fc2(x)return x

加载并打印模型:

#加载并打印模型
from torchinfo import summarymodel = Model().to(device)
summary(model)

在这里插入图片描述

五、训练模型

1、设置超参数

  • torch.optim是一个实现了各种优化算法的库。大部分常用的方法得到支持,并且接口具备足够的通用性,使得未来能够集成更加复杂的方法。
  • 为了使用torch.optim,你需要构建一个optimizer对象。这个对象能够保持当前参数状态并基于计算得到的梯度进行参数更新。
  • 其中的SGD是optim中的一个算法(优化器):随机梯度下降算法
  • 动手学深度学习-多层感知机中:updater = torch.optim.SGD(params, lr=lr)。其中的updater就是一个optimizer对象。“”"
loss_fn = nn.CrossEntropyLoss() #创建损失函数
learning_rate = 1e-2
opt = torch.optim.SGD(model.parameters(), lr = learning_rate) #待优化参数的iterable(w和b的迭代), 学习率

2、编写训练函数

  • .item():求出张量具体位置的元素值的高精度值
def train(dataloader, model, loss_fn, optimizer):size = len(dataloader.dataset) #训练集的大小, 一共60000张照片num_batches = len(dataloader) #批次数目,1875(60000/32)train_loss, train_acc = 0, 0 #初始化训练损失和正确率for X, y in dataloader: # 获取图片及其标签X, y = X.to(device), y.to(device)# 计算预测误差pred = model(X) #网络输出loss = loss_fn(pred, y) # 计算网络输出和真实值之间的差距,targets为真实值,计算两者差值即为损失# 反向传播optimizer.zero_grad() # grad属性归0loss.backward() # 反向传播optimizer.step() # 每一步自动更新#记录acc和 losstrain_acc += (pred.argmax(1) == y).type(torch.float).sum().item()train_loss += loss.item()train_acc /= sizetrain_loss /= num_batchesreturn train_acc, train_loss

3、编写测试函数

def test(dataloader, model, loss_fn):
size = len(dataloader.dataset) #测试集的大小,一共10000张照片
num_batches = len(dataloader)  #批次数目,313(10000/32=312.5,向上取整)
test_loss, test_acc =0, 0# 当不进行训练时,停止梯度更新,节省计算内存消耗
with torch.no_grad():for imgs, target in dataloader:imgs, target = imgs.to(device), target.to(device)#计算Losstarget_pred = model(imgs)loss = loss_fn(target_pred, target)test_loss += loss.item()test_acc += (target_pred.argmax(1) == target).type(torch.float).sum().item()test_acc /= size
test_loss /= num_batchesreturn test_acc, test_loss

4、正式训练

epochs = 5
train_loss = []
train_acc = []
test_loss = []
test_acc = []for epoch in range(epochs):
model.train()
epoch_train_acc, epoch_train_loss = train(train_dl, model, loss_fn, opt)model.eval()
epoch_test_acc, epoch_test_loss = test(test_dl, model, loss_fn)train_acc.append(epoch_train_acc)
train_loss.append(epoch_train_loss)
test_loss.append(epoch_test_loss)
test_acc.append(epoch_test_acc)template = ('Epoch:{:2d}, Train_acc:{:.1f}%, Train_loss:{:.3f}, Test_acc:{:.1f}%, Test_loss:{:.3f}')
print(template.format(epoch+1, epoch_train_acc*100, epoch_train_loss, epoch_test_acc*100, epoch_test_loss))
print('Done')

在这里插入图片描述

六、结果可视化

import matplotlib.pyplot as plt
#隐藏警告
import warnings
warnings.filterwarnings("ignore") # 忽视警告
plt.rcParams['font.sans-serif'] = ['SimHei'] #用来正常显示中文标签
plt.rcParams['axes.unicode_minus'] = False # 用来正常显示正负号
plt.rcParams['figure.dpi'] = 100 # 分辨率epochs_range = range(epochs)plt.figure(figsize = (12, 3))plt.subplot(1, 2, 1)
plt.plot(epochs_range, train_acc, label = 'Training Accuracy')
plt.plot(epochs_range, test_acc, label = 'Test Accuracy')
plt.legend(loc = 'lower right')
plt.title('Training and Validation Aaccuracy')plt.subplot(1, 2, 2)
plt.plot(epochs_range, train_loss, label = 'Training Loss')
plt.plot(epochs_range, test_loss, label = 'Test Loss')
plt.legend(loc = 'lower right')
plt.title('Training and Validation Loss')plt.show()

在这里插入图片描述

七、总结

该项目花了整整一天的时间,自己能理解的部分为目录一到四和七,从构建CNN网络开始就略有乏力,训练模型就完全看不懂了,自己也是尽最大程度的把各函数及其参数搜索并记忆。从结果来看,还是自身基本知识掌握的不到位,连CNN网络的概念都不清楚,下一步的计划是把吴恩达深度学习的视频和课后作业刷完,至少要明白卷积,池化,全连接层的定义和输出的结果以及这些层在背后的意义。

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

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

相关文章

机器学习与深度学习的基本概念

目录 机器学习是什么? 机器学习的任务 回归Regression 分类Classification 创造学习Structed Learing 机器学习怎么找这个函数 定义含未知参数的函数 定义loss损失函数 定义优化器optimization 写出一个更复杂的有未知参数的函数 sigmoid 基本推理过程 si…

一套Altair Feko复杂结构模型散射和天线辐射仿真建模攻略

导读:Feko软件广泛应用于电磁散射、电磁辐射仿真,例如:天线、天线布局、天线罩、屏蔽效能、电磁散射、频选结构、线束EMC等方面。问题种类繁多,但是无论仿真哪一类问题,其仿真流程是相同的,我们只需掌握了这…

使用 Echarts 插件完成中国旅游地图

目录前言:什么是 Echarts 插件具体实现思路中国旅游地图成品展示步骤:完成中国旅游地图代码总结:前言: 大家都知道,一般情况下,想要使用前端设置一个 中国旅游地图 需要使用 canvas 画布进行编写&#xff…

基于ARM架构openEuler系统通过qemu模拟器自动安装启动ARM架构的openEuler虚拟机

【原文链接】基于ARM架构openEuler系统通过qemu模拟器自动安装启动ARM架构的openEuler虚拟机 文章目录一、基础准备工作二、自动创建基于dhcp自动获取ip地址的openEuler虚拟机三、自动创建配置静态IP地址的openEuler虚拟一、基础准备工作 (1)下载ARM架构…

[附源码]Python计算机毕业设计Django校园订餐系统

项目运行 环境配置: Pychram社区版 python3.7.7 Mysql5.7 HBuilderXlist pipNavicat11Djangonodejs。 项目技术: django python Vue 等等组成,B/S模式 pychram管理等等。 环境需要 1.运行环境:最好是python3.7.7,…

【Linux|树莓派】分文件编程以及静态库动态库

一、分文件编程 简单来说树莓派的分文件编程就是将一个项目的代码放在不同的文件里面&#xff0c;然后在主函数添加一个头文件&#xff0c;这样会使#控制字体颜色主程序变得简单。 在编译的时候要将主函数和功能函数一起编译&#xff1a; 注意&#xff1a;include <stdio.h…

Matplotlib入门[04]——处理图像

Matplotlib入门[04]——处理图像 参考&#xff1a; https://ailearning.apachecn.org/Matplotlib官网 图片来源&#xff1a;百度&#xff08;如有侵权&#xff0c;立删&#xff09; 使用Jupyter进行练习 import matplotlib.pyplot as plt import matplotlib.image as mpimg imp…

【Java学习Note】第8章 多线程

8. 多线程 文章目录8. 多线程8.1 程序、进程、线程8.2 线程的创建8.2.1 继承Thread类-创建线程方法之一8.2.2 Thread常用方法8.2.3 实现Runnable接口-创建线程方法之二8.2.4 两种多线程的区别8.3 线程得调度8.4 线程的生命周期8.5 线程的同步8.5.1 线程同步--Synchronized8.5.2…

CUDA入门和网络加速学习(一)

0. 简介 最近作者希望系统性的去学习一下CUDA加速的相关知识&#xff0c;正好看到深蓝学院有这一门课程。所以这里作者以此课程来作为主线来进行记录分享&#xff0c;方便能给CUDA网络加速学习的萌新们去提供一定的帮助。 1. GPU与CPU区别 处理器指标一般主要分为两大类&…

使用react-grid-layout和react-full-screen实现一个可自定义和全屏展示的dashboard页面

文章目录使用react-grid-layout和react-full-screen实现一个可自定义和全屏展示的dashboard页面具体实现代码展示主展示页面懒加载组件组件加载时展示的组件dashboard菜单组件具体的图表组件Demo演示使用react-grid-layout和react-full-screen实现一个可自定义和全屏展示的dash…

【微服务】SpringCloud中OpenFeign请求处理及负载均衡流程

&#x1f496; Spring家族及微服务系列文章 ✨【微服务】SpringCloud中Ribbon的WeightedResponseTimeRule策略 ✨【微服务】SpringCloud中Ribbon的轮询(RoundRobinRule)与重试(RetryRule)策略 ✨【微服务】SpringCloud中Ribbon集成Eureka实现负载均衡 ✨【微服务】SpringCloud…

EMQ 宣布推出 LF Edge eKuiper 全新 Logo 标识

全球领先的开源物联网数据基础设施软件供应商 EMQ 映云科技宣布,即日起,将正式启用全新的 LF Edge eKuiper(以下简称 eKuiper)产品 Logo。焕然一新的 eKuiper 产品 Logo 标志着 EMQ 在不断提升品牌全球化战略之上,对于打造高性能、高可用、高安全的世界级开源软件产品的极致追求…

【1805. 字符串中不同整数的数目】

来源&#xff1a;力扣&#xff08;LeetCode&#xff09; 描述&#xff1a; 给你一个字符串 word &#xff0c;该字符串由数字和小写英文字母组成。 请你用空格替换每个不是数字的字符。例如&#xff0c;"a123bc34d8ef34" 将会变成 " 123 34 8 34" 。注意…

面试题: LEAD 和 LAG 求每个用户的页面停留时长

我们先来看看这两个函数的语法&#xff1a; LEAD(col,n,default) OVER() 说明&#xff1a; 用于统计窗口内向下第n行的值参数1&#xff1a; 为要取值的列名参数2&#xff1a; 为向下第n行&#xff0c;默认值为1&#xff0c;这个值是固定的&#xff0c;不能动态的变化参数3&am…

深度学习-全卷积神经网络(FCN)

1. 简介 全卷积神经网络&#xff08;Fully Convolutional Networks&#xff0c;FCN&#xff09;是Jonathan Long等人于2015年在Fully Convolutional Networks for Semantic Segmentation一文中提出的用于图像语义分割的一种框架&#xff0c;是深度学习用于语义分割领域的开山之…

国际学校妈妈哭诉IB太难:中国孩子都不知道怎么答题?

听别人说考国际学校的IB体系相对简单直到我看到IB试题才知道其实IB一点都不容易特别对于中国学生有大量写论文的部分来看看IB的真题有些学生真的很难下笔不知道怎么答题啊&#xff01;商科生物 题目都是非常考验综合能力的&#xff0c;学生需要掌握很多知识点并融会贯通&#x…

cengbox2靶机(hydra爆破、公私钥免密登录)

环境准备 靶机链接&#xff1a;百度网盘 请输入提取码 提取码&#xff1a;zdpr 虚拟机网络链接模式&#xff1a;桥接模式 攻击机系统&#xff1a;kali linux 2021.1 信息收集 1.arp-scan -l探测目标靶机ip 2.nmap -p- -A -T4 192.168.1.107 探测目标靶机开放端口和服务 …

Locust学习记录5-任务属性【Task】

Task 当负载测试开始时&#xff0c;将为每个模拟用户创建一个User类的实例&#xff0c;他们将开始在自己的绿色线程中运行。当这些用户运行时&#xff0c;他们选择他们执行的任务&#xff0c;休眠一段时间&#xff0c;然后选择一个新任务。 这些任务时普通的python可调用文件…

服务访问质量(QoS)介绍与技术 一

个人简介&#xff1a;云计算网络运维专业人员&#xff0c;了解运维知识&#xff0c;掌握TCP/IP协议&#xff0c;每天分享网络运维知识与技能。个人爱好: 编程&#xff0c;打篮球&#xff0c;计算机知识个人名言&#xff1a;海不辞水&#xff0c;故能成其大&#xff1b;山不辞石…

K8S Pod控制器详细讲解

文章目录一、Pod控制器介绍二、ReplicaSet(RS)三、Deployment(Deploy)1.镜像更新&#xff1a;2.版本回退3.金丝雀发布/灰度发布四、Horizontal Pod Autoscaler(HPA)五、DaemonSet(DS)六、Job七、CronJob(CJ)结尾一、Pod控制器介绍 Pod是kubernetes的最小管理单元&#xff0c;在…