热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

深度学习在图像分类中的应用ーー利用Pytorch从零开始创建CNN

引言本文将解释一个卷积神经网络(CNN)的一般结构,从而有助于了解如何分类不同类别的图像(在我们的案例中不同类型的动物),使用PyTorch从头开始编写

引言

 

本文将解释一个卷积神经网络(CNN)的一般结构,从而有助于了解如何分类不同类别的图像(在我们的案例中不同类型的动物) ,使用 PyTorch 从头开始编写一个 CNN 模型。

先决条件


  • Python 基础知识

  • 对神经网络的基本理解

  • 对卷积型神经网络(CNN)的基本理解

     

使用的数据集

Animals-10 数据集,小伙伴们可以从这个网址中下载:https://www.kaggle.com/alessiocorrado99/animals10

开始编程

步骤1:(下载数据集)


  • 可以从上述网址中下载数据集

  • 这个数据集包含10个类别的28,000张图片:狗,猫,马,蜘蛛,蝴蝶,鸡,羊,牛,松鼠和大象

图片

步骤2:(创建数据集和数据加载器来加载这些图像)dataset_path = 'BasicCNN_Pytorch/raw-img'

mean = torch.tensor([0.485, 0.456, 0.406], dtype=torch.float32)std = torch.tensor([0.229, 0.224, 0.225], dtype=torch.float32)# Transformation function to be applied on images# 1. Horizontally Flip the image with a probability of 30%# 2. Randomly Rotate the image at an angle between -40 to 40 degress.# 3. Resize each images to a smallest size of 300 pixels maintaining aspect ratio# 4. Crop a square of size 256x256 from the center of image# 5. Convert Image to a Pytorch Tensor# 6. Normalize the pytorch's tensor using mean & std of imagenettransform = transforms.Compose([ transforms.RandomHorizontalFlip(p=0.3), transforms.RandomRotation(degrees=40),
transforms.Resize(300), transforms.CenterCrop(256),
transforms.ToTensor(), transforms.Normalize(mean=mean, std=std)])
# Create a dataset by from the dataset folder by applying the above transformation.dataset = torchvision.datasets.ImageFolder(dataset_path, transform=transform)# Split the dataset into train & test containing 21000 and 5179 images respectively.train_dataset, test_dataset = torch.utils.data.random_split(dataset, (21000, 5179))
# Create a Train DataLoader using Train Datasettrain_dataloader = torch.utils.data.DataLoader( dataset=train_dataset, batch_size=16, shuffle=False, num_workers=4)# Create a Test DataLoader using Test Datasettest_dataloader = torch.utils.data.DataLoader( dataset=test_dataset, batch_size=16, shuffle=False, num_workers=4)

步骤3:创建 CNN 模型架构

让我们创建一个简单的 CNN 模型架构。

class MyModel(nn.Module): def __init__(self): super(MyModel, self).__init__() self.model = nn.Sequential( nn.Conv2d(3, 16, kernel_size=3), nn.ReLU(), nn.Conv2d(16, 16, kernel_size=3), nn.ReLU(), nn.MaxPool2d(2,2),
nn.Conv2d(16, 32, kernel_size=3), nn.ReLU(), nn.Conv2d(32, 32, kernel_size=3), nn.ReLU(), nn.MaxPool2d(2,2),
nn.Conv2d(32, 64, kernel_size=3), nn.ReLU(), nn.Conv2d(64, 64, kernel_size=3), nn.ReLU(), nn.MaxPool2d(2,2),
nn.Conv2d(64, 128, kernel_size=3), nn.ReLU(), nn.Conv2d(128, 128, kernel_size=3), nn.ReLU(), nn.MaxPool2d(2,2),
nn.Conv2d(128, 256, kernel_size=3), nn.ReLU(), nn.Conv2d(256, 256, kernel_size=3), nn.ReLU(), nn.MaxPool2d(2,2),
).to(device) self.classifier = nn.Sequential( nn.Flatten(), nn.Dropout(0.25), nn.Linear(4096, 256), nn.ReLU(),
nn.Dropout(0.5), nn.Linear(256, 10) ).to(device) def forward(self, x): x = self.model(x) x = self.classifier(x) return xmodel = MyModel().to(device)summary(model, (3,256,256))

像所有一般的 CNN 体系结构一样,我们的模型也有两个组件:

 


  1. 一组卷积后面跟着一个激活函数(在我们的例子中使用 ReLU)和一个最大池层

  2. 一个线性分类层,将图像分为3类(猫,狗和熊猫)

图片

CNN 模型架构


  • 该模型包含大约223万个参数

  • 当我们沿着卷积层向下走时,我们观察到通道的数量从3个(RGB 图像)增加到16个、32个、64个、128个,然后增加到256个

  • ReLU 层在每次卷积运算后提供非线性操作

  • 由于我们的最大池化层,因此随着通道数目的增加,图像的高度和宽度也随之减小

  • 我们在我们的分类层添加了 dropout,防止模型过拟合

步骤4:定义模型、优化器和损失函数

 

我们使用了学习率为0.0001的 Adam 优化器和交叉熵损失函数。

lr = 0.0001model = MyModel().to(device)
optimizer = torch.optim.Adam(model.parameters(), lr=lr)criterion = nn.CrossEntropyLoss()

步骤5:开始训练

终于到了我们都在等待的时刻,也就是训练模型的时刻。对于训练和测试,我创建了这两个辅助函数。

def Train(epoch, print_every=50): total_loss = 0 start_time = time() accuracy = [] for i, batch in enumerate(train_dataloader, 1): minput = batch[0].to(device) # Get batch of images from our train dataloader target = batch[1].to(device) # Get the corresponding target(0, 1 or 2) representing cats, dogs or pandas moutput = model(minput) # output by our model loss = criterion(moutput, target) # compute cross entropy loss total_loss += loss.item()
optimizer.zero_grad() # Clear the gradients if exists. (Gradients are used for back-propogation.) loss.backward() # Back propogate the losses optimizer.step() # Update Model parameters argmax = moutput.argmax(dim=1) # Get the class index with maximum probability predicted by the model accuracy.append((target==argmax).sum().item() / target.shape[0]) # calculate accuracy by comparing to target tensor
if i%print_every == 0: print('Epoch: [{}]/({}/{}), Train Loss: {:.4f}, Accuracy: {:.2f}, Time: {:.2f} sec'.format( epoch, i, len(train_dataloader), loss.item(), sum(accuracy)/len(accuracy), time()-start_time ))     return total_loss / len(train_dataloader) # Returning Average Training Loss

def Test(epoch): total_loss = 0 start_time = time()
accuracy = [] with torch.no_grad(): # disable calculations of gradients for all pytorch operations inside the block for i, batch in enumerate(test_dataloader): minput = batch[0].to(device) # Get batch of images from our test dataloader target = batch[1].to(device) # Get the corresponding target(0, 1 or 2) representing cats, dogs or pandas moutput = model(minput) # output by our model
loss = criterion(moutput, target) # compute cross entropy loss total_loss += loss.item() # To get the probabilities for different classes we need to apply a softmax operation on moutput argmax = moutput.argmax(dim=1) # Find the index(0, 1 or 2) with maximum score (which denotes class with maximum probability) accuracy.append((target==argmax).sum().item() / target.shape[0]) # Find the accuracy of the batch by comparing it with actual targets print('Epoch: [{}], Test Loss: {:.4f}, Accuracy: {:.2f}, Time: {:.2f} sec'.format( epoch, total_loss/len(test_dataloader), sum(accuracy)/len(accuracy), time()-start_time ))    return total_loss/len(test_dataloader) # Returning Average Testing LossHosted on Jovian

现在让我们开始训练:

感谢我们在上面创建的 helper 函数,我们可以使用下面的代码片段轻松地开始训练过程。

Test(0)
train_loss = []test_loss = []
for epoch in range(1, 51): train_loss.append(Train(epoch,200)) test_loss.append(Test(epoch))
print('\n') if epoch % 10 == 0: torch.save(model, 'model_'+str(epoch)+'.pth')

我们正在训练该模型50个 epoch,并在每10个 epoch 之后将其保存到磁盘。

这是我们在训练中得到的输出(部分):

图片

图片


  • 在谷歌 colab 使用 Tesla T4 GPU 训练这个步骤花了大约2个小时(50个 epoch);

  • 正如我们可以看到的,准确率从第1个 epoch 后的21% 上升到第50个 epoch 后的75% 。(经过另外50个 epoch 的训练,准确率达到了78%)

  • 我们非常基本的 CNN 模型只有2.23 M 的参数

评估模型

我们绘制一下训练和测试损失:


  • 大约20个 epoch 之后,我们可以看到曲线明显的变化

图片

现在让我们用一些随机的图片来测试一下。

图片

·  END  ·

原文 https://mp.weixin.qq.com/s/m8w_G4ea7oOb3J-J7rxQ3A


推荐阅读
  • 通过使用CIFAR-10数据集,本文详细介绍了如何快速掌握Mixup数据增强技术,并展示了该方法在图像分类任务中的显著效果。实验结果表明,Mixup能够有效提高模型的泛化能力和分类精度,为图像识别领域的研究提供了有价值的参考。 ... [详细]
  • Ihavetwomethodsofgeneratingmdistinctrandomnumbersintherange[0..n-1]我有两种方法在范围[0.n-1]中生 ... [详细]
  • 【图像分类实战】利用DenseNet在PyTorch中实现秃头识别
    本文详细介绍了如何使用DenseNet模型在PyTorch框架下实现秃头识别。首先,文章概述了项目所需的库和全局参数设置。接着,对图像进行预处理并读取数据集。随后,构建并配置DenseNet模型,设置训练和验证流程。最后,通过测试阶段验证模型性能,并提供了完整的代码实现。本文不仅涵盖了技术细节,还提供了实用的操作指南,适合初学者和有经验的研究人员参考。 ... [详细]
  • 探索聚类分析中的K-Means与DBSCAN算法及其应用
    聚类分析是一种用于解决样本或特征分类问题的统计分析方法,也是数据挖掘领域的重要算法之一。本文主要探讨了K-Means和DBSCAN两种聚类算法的原理及其应用场景。K-Means算法通过迭代优化簇中心来实现数据点的划分,适用于球形分布的数据集;而DBSCAN算法则基于密度进行聚类,能够有效识别任意形状的簇,并且对噪声数据具有较好的鲁棒性。通过对这两种算法的对比分析,本文旨在为实际应用中选择合适的聚类方法提供参考。 ... [详细]
  • 从2019年AI顶级会议最佳论文,探索深度学习的理论根基与前沿进展 ... [详细]
  • 在高清节目的高比特率传输过程中,使用外接USB硬盘进行时间平移(timeshift)时,出现了性能不足和流数据丢失的问题。通过深入研究,我们发现通过对图像组(GOP)和图像头(I-frame)的精确定位技术进行优化,可以显著提升系统的性能和稳定性。本研究提出了改进的图像组与图像头定位算法,有效减少了数据丢失,提高了流媒体传输的效率和质量。 ... [详细]
  • 目录预备知识导包构建数据集神经网络结构训练测试精度可视化计算模型精度损失可视化输出网络结构信息训练神经网络定义参数载入数据载入神经网络结构、损失及优化训练及测试损失、精度可视化qu ... [详细]
  • javascript分页类支持页码格式
    前端时间因为项目需要,要对一个产品下所有的附属图片进行分页显示,没考虑ajax一张张请求,所以干脆一次性全部把图片out,然 ... [详细]
  • 2018 HDU 多校联合第五场 G题:Glad You Game(线段树优化解法)
    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=6356在《Glad You Game》中,Steve 面临一个复杂的区间操作问题。该题可以通过线段树进行高效优化。具体来说,线段树能够快速处理区间更新和查询操作,从而大大提高了算法的效率。本文详细介绍了线段树的构建和维护方法,并给出了具体的代码实现,帮助读者更好地理解和应用这一数据结构。 ... [详细]
  • 在深入研究 UniApp 封装请求时,发现其请求 API 方法中使用了 `then` 和 `catch` 函数。通过详细分析,了解到这些函数是 Promise 对象的核心组成部分。Promise 是一种用于处理异步操作的结果的标准化方式,它提供了一种更清晰、更可控的方法来管理复杂的异步流程。本文将详细介绍 Promise 的基本概念、结构和常见应用场景,帮助开发者更好地理解和使用这一强大的工具。 ... [详细]
  • HTML 页面中调用 JavaScript 函数生成随机数值并自动展示
    在HTML页面中,通过调用JavaScript函数生成随机数值,并将其自动展示在页面上。具体实现包括构建HTML页面结构,定义JavaScript函数以生成随机数,以及在页面加载时自动调用该函数并将结果呈现给用户。 ... [详细]
  • 机器学习中的标准化缩放、最小-最大缩放及鲁棒缩放技术解析 ... [详细]
  • 在HTML5应用中,Accordion(手风琴,又称抽屉)效果因其独特的展开和折叠样式而广泛使用。本文探讨了三种不同的Accordion交互效果,通过层次结构优化信息展示和页面布局,提升用户体验。这些效果不仅增强了视觉效果,还提高了内容的可访问性和互动性。 ... [详细]
  • 2019年斯坦福大学CS224n课程笔记:深度学习在自然语言处理中的应用——Word2Vec与GloVe模型解析
    本文详细解析了2019年斯坦福大学CS224n课程中关于深度学习在自然语言处理(NLP)领域的应用,重点探讨了Word2Vec和GloVe两种词嵌入模型的原理与实现方法。通过具体案例分析,深入阐述了这两种模型在提升NLP任务性能方面的优势与应用场景。 ... [详细]
  • 根据特定准则优化阵列元素的最低总和 ... [详细]
author-avatar
ni是我的另一半
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有