使用 PyTorch 进行高效图像分割:第 3 部分

一、说明

        在这个由 4 部分组成的系列中,我们将使用 PyTorch 中的深度学习技术从头开始逐步实现图像分割。本部分将重点介绍如何使用深度可分离卷积来优化我们的 CNN 基线模型,以减少可训练参数的数量,使模型可部署在移动设备和其他边缘设备上。

图 1:使用具有深度可分离卷积而不是常规卷积的 CNN 运行图像分割的结果。从上到下,输入图像、地面实况分割掩码和预测分割掩码。 

二、文章大纲

        在本文中,我们将增强我们之前构建的卷积神经网络(CNN),以减少网络中可学习参数的数量。在输入图像中识别宠物像素(属于猫、狗、仓鼠等的像素)的任务保持不变。我们选择的网络仍将是SegNet,我们唯一要做的改变是用深度可分离卷积(DSC)替换我们的卷积层。在我们这样做之前,我们将深入研究深度可分离卷积的理论和实践,并欣赏该技术背后的想法。

        在本文中,我们将参考此笔记本中的代码和结果进行模型训练,并引用此笔记本中的代码和结果进行 DSC 入门。如果要重现结果,则需要一个 GPU 来确保第一个笔记本在合理的时间内完成运行。第二个笔记本可以在常规 CPU 上运行。

三、本系列文章

        本系列面向所有深度学习经验水平的读者。如果您想了解深度学习和视觉AI的实践以及一些扎实的理论和实践经验,那么您来对地方了!这将是一个由 4 部分组成的系列,包含以下文章:

  1. 概念和想法
  2. 基于 CNN 的模型
  3. 深度可分离卷积(本文)
  4. 基于视觉变压器的模型

四、介绍

        让我们从模型大小和计算成本的角度仔细研究卷积开始讨论。可训练参数的数量可以很好地指示模型的大小,张量运算的数量反映了模型的复杂性或计算成本。考虑我们有一个卷积层,其中包含 n 个大小为 dk x dk 的过滤器。进一步假设该层处理形状为 m x h x w 的输入,其中 m 是输入通道的数量,h 和 w 分别是高度和宽度尺寸。在这种情况下,卷积层将产生形状为 n x h x w 的输出,如图 2 所示。我们假设卷积使用 stride=1。让我们继续根据可训练参数和计算成本来评估此设置。

图 2:应用于输入以产生输出的常规卷积滤波器。假设步幅=1,填充=dk-2。来源:高效深度学习书

        可训练参数的评估:我们有 n 个过滤器,每个过滤器都有 m x dk x dk 可学习参数。这导致总共有 n x m x dk x dk 可学习参数。忽略偏见术语以简化此讨论。让我们看看下面的 PyTorch 代码来验证我们的理解。

import torch
from torch import nn
def num_parameters(m):
return sum([p.numel() for p in m.parameters()])
dk, m, n = 3, 16, 32
print(f"Expected number of parameters: {m * dk * dk * n}")
conv1 = nn.Conv2d(in_channels=m, out_channels=n, kernel_size=dk, bias=False)
print(f"Actual number of parameters: {num_parameters(conv1)}")

        打印以下内容。

Expected number of parameters: 4608
Actual number of parameters: 4608

        现在,让我们评估卷积的计算成本。

        计算成本评估:当在大小为 h x w 的输入上以步幅=1 和填充 = dk-2 运行时,形状为 m x dk x dk 的单个卷积过滤器将应用卷积过滤器 h x w 次,对于大小为 dk x dk 的每个图像部分总共应用 h x w 部分一次。它导致每个滤波器或输出通道的成本为 m x dk x dk x h x w。由于我们希望计算 n 个输出通道,因此总成本将为 m x dk x dk x h x n。让我们继续使用torchinfo PyTorch包来验证这一点。

from torchinfo import summary
h, w = 128, 128
print(f"Expected total multiplies: {m * dk * dk * h * w * n}")
summary(conv1, input_size=(1, m, h, w))

将打印以下内容。

Expected total multiplies: 75497472==========================================================================================
Layer (type:depth-idx)                   Output Shape              Param #
==========================================================================================
Conv2d                                   [1, 32, 128, 128]         4,608
==========================================================================================
Total params: 4,608
Trainable params: 4,608
Non-trainable params: 0
Total mult-adds (M): 75.50
==========================================================================================
Input size (MB): 1.05
Forward/backward pass size (MB): 4.19
Params size (MB): 0.02
Estimated Total Size (MB): 5.26
==========================================================================================

        如果我们暂时忽略卷积层的实现细节,我们会意识到,在高层次上,卷积层只是将 m x h x w 输入转换为 n x h x w 输出。转换是通过可训练的过滤器实现的,这些过滤器在看到输入时逐渐学习特征。接下来的问题是:是否有可能使用更少的可学习参数来实现这种转换,同时确保层的学习能力的最小妥协?提出了深度可分卷积来回答这个确切的问题。让我们详细了解它们,并了解它们在我们的评估指标上是如何叠加的。

五、深度可分离卷积

        深度可分卷积(DSC)的概念最初是由Laurent Sifre在他们的博士论文“用于图像分类的刚性运动散射”中提出的。从那时起,它们已成功用于各种流行的深度卷积网络,如XceptionNet和MobileNet。

        常规卷积和 DSC 之间的主要区别在于 DSC 由 2 个卷积组成,如下所述:

  1. 深度分组卷积,其中输入通道数 m 等于输出通道数,使得每个输出通道仅受单个输入通道的影响。在 PyTorch 中,这被称为“分组”卷积。您可以在此处阅读有关 PyTorch 中分组卷积的更多信息。
  2. 逐点卷积(滤波器大小=1),其操作类似于常规卷积,因此n个滤波器中的每个都在所有m个输入通道上运行以产生单个输出值。

图 3:应用于输入以产生输出的深度可分离卷积滤波器。假设步幅=1填充=dk-2。来源:高效深度学习书

        让我们执行与 DSC 常规卷积相同的练习,并计算可训练参数和计算的数量。

        可训练参数的评估:“分组”卷积有 m 个滤波器,每个滤波器都有 dk x dk 可学习参数,可生成 m 个输出通道。这导致总共 m x dk x dk 可学习参数。逐点卷积有 n 个大小为 m x 1 x 1 的过滤器,其加起来最多有 n x m x 1 x 1 个可学习参数。让我们看看下面的 PyTorch 代码来验证我们的理解。

class DepthwiseSeparableConv(nn.Sequential):def __init__(self, chin, chout, dk):super().__init__(# Depthwise convolutionnn.Conv2d(chin, chin, kernel_size=dk, stride=1, padding=dk-2, bias=False, groups=chin),# Pointwise convolutionnn.Conv2d(chin, chout, kernel_size=1, bias=False),)conv2 = DepthwiseSeparableConv(chin=m, chout=n, dk=dk)
print(f"Expected number of parameters: {m * dk * dk + m * 1 * 1 * n}")
print(f"Actual number of parameters: {num_parameters(conv2)}")

        这将打印。

Expected number of parameters: 656
Actual number of parameters: 656

        我们可以看到 DSC 版本的参数大约减少了 7 倍。接下来,让我们将注意力集中在 DSC 层的计算成本上。

        计算成本评估:假设我们的输入具有空间维度 m x h x w。在DSC的分组卷积段中,我们有m个过滤器,每个过滤器的大小为dk x dk。滤波器应用于其相应的输入通道,导致段成本为 m x dk x dk x h x w。对于逐点卷积,我们应用 n 个大小为 m x 1 x 1 的滤波器来产生 个输出通道。这导致段成本为 n x m x 1 x 1 x h x w。我们需要将分组和逐点操作的成本相加以计算总成本。让我们继续使用torchinfo PyTorch包来验证这一点。

print(f"Expected total multiplies: {m * dk * dk * h * w + m * 1 * 1 * h * w * n}")
s2 = summary(conv2, input_size=(1, m, h, w))
print(f"Actual multiplies: {s2.total_mult_adds}")
print(s2)

这将打印。

Expected total multiplies: 10747904
Actual multiplies: 10747904
==========================================================================================
Layer (type:depth-idx)                   Output Shape              Param #
==========================================================================================
DepthwiseSeparableConv                   [1, 32, 128, 128]         --
├─Conv2d: 1-1                            [1, 16, 128, 128]         144
├─Conv2d: 1-2                            [1, 32, 128, 128]         512
==========================================================================================
Total params: 656
Trainable params: 656
Non-trainable params: 0
Total mult-adds (M): 10.75
==========================================================================================
Input size (MB): 1.05
Forward/backward pass size (MB): 6.29
Params size (MB): 0.00
Estimated Total Size (MB): 7.34
========================================================================================== 

让我们比较两个卷积的大小和成本,举几个例子来获得一些直觉。

六、常规和深度可分离卷积的尺寸和成本比较

        为了比较常规卷积和深度可分离卷积的大小和成本,我们将假设网络的输入大小为 128 x 128,内核大小为 3 x 3,以及一个逐渐将空间维度减半并将通道维度数量加倍的网络。我们假设每一步都有一个 2D-conv 层,但实际上,可能还有更多。

图 4:比较常规和深度可分离卷积的可训练参数(大小)和多加(成本)的数量。我们还显示了 2 种卷积的大小和成本之比。资料来源:作者。

您可以看到,平均而言,DSC 的大小和计算成本约为上述配置常规卷积成本的 11% 到 12%。

图 5:常规 VS/s DSC 的相对大小和成本。资料来源:作者。

        现在我们已经对卷积的类型及其相对成本有了很好的了解,你一定想知道使用 DSC 是否有任何缺点。 到目前为止,我们所看到的一切似乎都表明它们在各个方面都更好!好吧,我们还没有考虑一个重要的方面,即它们对我们模型准确性的影响。让我们通过下面的实验深入了解它。

七、使用深度可分离卷积的SegNet

        此笔记本包含此部分的所有代码。

        我们将调整上一篇文章中的SegNet模型,并用DSC层替换所有常规卷积层。完成此操作后,我们注意到笔记本中的参数数量从 15.27M 下降到 1.75M,减少了 88.5%!这与我们之前估计的网络可训练参数数量减少 11% 到 12% 一致。

在模型训练和验证期间使用了与以前类似的配置。配置指定如下。

  1. 随机水平翻转颜色抖动数据增强应用于训练集以防止过度拟合
  2. 在非宽高比保留调整大小操作中将图像大小调整为 128x128 像素
  3. 不会对图像应用任何输入归一化,而是使用批量归一化层作为模型的第一层
  4. 该模型使用 LR 为 20.0 且没有 LR 调度程序的 Adam 优化器训练了 001 个 epoch
  5. 交叉熵损失函数用于将像素分类为属于宠物、背景或宠物边框

该模型在 86 个训练周期后实现了 96.20% 的验证准确率。这低于模型在相同数量的训练周期内使用常规卷积所达到的 88.28% 的准确率。我们已经通过实验确定,训练更多的 epoch 可以提高两个模型的准确性,所以 20 个 epoch 绝对不是训练周期的结束。出于本文的目的,我们停在 20 个纪元,以便进行演示。

我们绘制了一个 gif,显示了模型如何学习预测验证集中 21 张图像的分割掩码。

图 6:一个 gif,显示了带有 DSC 的 SegNet 模型如何学习预测验证集中 21 张图像的分割掩码。来源:作者

现在我们已经了解了模型在训练周期中是如何进展的,让我们将模型的训练周期与常规卷积和 DSC 进行比较。

八、精度比较

        我们发现使用常规卷积和DSC查看模型的训练周期很有用。我们注意到的主要区别是在训练的早期阶段(时期),之后两个模型大致进入相同的预测流。事实上,在训练了两个模型 100 个 epoch 之后,我们注意到使用 DSC 的模型的精度仅比具有常规卷积的模型低约 1%。这与我们对20个训练时期的观察结果一致。

图 7:一个 gif,显示了 SegNet 模型使用常规卷积与 DSC 预测的分割掩码的进展。资料来源:作者。

        你会注意到,两个模型在仅仅 6 个训练周期后就大致正确地得到了预测——也就是说,人们可以直观地看到模型正在预测一些有用的东西。然后,训练模型的大部分艰苦工作都在确保预测的面具的边界尽可能紧密,并尽可能接近图像中的实际宠物。这意味着,虽然人们可以预期在后期训练时期准确性的绝对提高较小,但这对预测质量的影响要大得多。我们注意到,在更高的绝对准确度值(从 89% 到 90%)下,准确度提高个位数会导致预测的显著定性改进。

九、与联合国网络模式的比较

        我们进行了一项实验,更改了许多超参数,重点是提高整体准确性,以了解此设置离接近最佳有多远。下面是该实验的配置。

  1. 图像尺寸:128 x 128 — 与迄今为止的实验相同
  2. 训练周期:100 — 当前实验训练了 20 个周期
  3. 增强:更多的增强,例如图像旋转,通道丢弃,随机块删除。我们使用Albumentations而不是Torchvision转换。蛋白为我们自动转换分割掩码
  4. LR 调度器:使用 StepLR 调度器,每 0 个列车周期衰减 8.25 倍
  5. 损失函数:我们尝试了 4 种不同的损失函数:交叉熵、焦点、骰子、加权交叉熵。骰子表现最差,而其余的几乎可以相互媲美。事实上,100 个 epoch 之后其余部分之间的最佳精度差异在小数点后的第 4 位(假设精度是 0.0 到 1.0 之间的数字)
  6. 卷积类型:常规
  7. 模型类型:UNet — 当前实验使用SegNet模型

        对于上述设置,我们实现了91.3%的最佳验证准确率。我们注意到图像大小会显著影响最佳验证精度。例如,当我们将图像大小更改为 256 x 256 时,最佳验证准确度高达 93.0%。但是,训练花费的时间要长得多,并且使用更多的内存,这意味着我们必须减小批量大小。

图 8:使用上述超参数训练 100 个训练时期的 UNet 模型的结果。资料来源:作者。

您可以看到,与我们迄今为止看到的预测相比,预测更加平滑和清晰。

十、结论

        在本系列的第 3 部分中,我们了解了深度可分离卷积 (DSC) 作为一种在不显著降低验证准确性的情况下减小模型大小和训练/推理成本的技术。我们了解了特定设置在常规和 DSC 之间的大小/成本权衡。

        我们展示了如何调整SegNet模型以在PyTorch中使用DSC。这种技术可以应用于任何深度CNN。事实上,我们可以有选择地用DSC替换一些卷积层——也就是说,我们不一定需要替换所有卷积层。选择要替换的图层将取决于您希望在模型大小/运行时成本和预测精度之间取得的平衡。此决定将取决于您的特定用例和部署设置。

        虽然本文训练了 20 个 epoch 的模型,但我们解释说这对于生产工作负载来说是不够的,并提供了一瞥如果为更多 epoch 训练模型可以期待什么。此外,我们还介绍了一些可以在模型训练期间调整的超参数。虽然此列表并不全面,但它应该可以让您了解为生产工作负载训练图像分割模型所需的复杂性和决策。

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

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

相关文章

opencv如何调用YOLOv5(无pytorch)

目录 一、前言 二.正文 2.1定义颜色 2.2目标检测主代码详解 2.3读取视频or图片进行检测 注意:opencv-python 本文使用的版本为4.5.2.52 一、前言 YOLO系列是one-stage且是基于深度学习的回归方法,而R-CNN、Fast-RCNN、Faster-RCNN等是two-stage且…

计算机网络第2章(物理层)

计算机网络第2章(物理层) 2.1 物理层的基本概念2.2 物理层下面的传输媒体2.2.1 导引型传输媒体2.2.2 非导引型传输媒体 2.3 传输方式2.3.1 串行传输和并行传输2.3.2 同步传输和异步传输2.3.3 单向通信(单工)、双向交替通信&#x…

很好的启用window10专业版系统自带的远程桌面

启用window10专业版系统自带的远程桌面 文章目录 启用window10专业版系统自带的远程桌面前言1.找到远程桌面的开关2. 找到“应用”项目3. 打开需要远程操作的电脑远程桌面功能 总结 前言 Windows操作系统作为应用最广泛的个人电脑操作系统,在我们身边几乎随处可见。…

分布式事务(4):两阶段提交协议与三阶段提交区别

1 两阶段提交协议 两阶段提交方案应用非常广泛,几乎所有商业OLTP数据库都支持XA协议。但是两阶段提交方案锁定资源时间长,对性能影响很大,基本不适合解决微服务事务问题。 缺点: 如果协调者宕机,参与者没有协调者指…

如何在window下cmd窗口执行linux指令?

1.Git:https://git-scm.com/downloads(官网地址) 2.根据自己的实际路径,添加两个环境变量 3.重启电脑

Kubernetes教程—查看 Pod 和节点

目标 了解 Kubernetes Pod。了解 Kubernetes 节点。对已部署的应用故障排除。 Kubernetes Pod 在模块 2 中创建 Deployment 时, Kubernetes 创建了一个 Pod 来托管你的应用实例。Pod 是 Kubernetes 抽象出来的, 表示一组一个或多个应用容器(如 Docker…

爬虫借助代理会让网速快点吗?

亲爱的程序员朋友们,你曾经遇到过爬虫网速慢的情况吗?别着急!今天我将和你一起探讨一下使用代理是否可以加速爬虫,让我们一起进入这个轻松又专业的知识分享。 一、原因和机制的解析 1.IP限制 某些网站为了保护资源和防止爬虫行…

线段树详解——影子宽度

OK,今天来讲一讲线段树~~ 线段树是什么线段树的实现线段树的时间复杂度线段树的应用线段树的节点结构其他操作和优化例题——影子宽度输入输出格式输入格式输出格式 输入输出样例输入样例输出样例 例题讲解 线段树是什么 线段树( S e g m e n t Segmen…

Goland 注释时自动在注释符号后添加空格

不得不说 JetBrains 旗下的 IDE 都好用,而且对于注释这块,使用 Ctrl / 进行注释的时候,大多会在每个注释符号后统一添加一个空格,比如 PyCharm 和 RubeMine 等。 # PyCharm # print("hello world") # RubyMine # req…

Confluent kafka 异常退出rd_tmpabuf_alloc0: rd kafka topic info_new_with_rack

rd_tmpabuf_alloc0: rd kafka topic info_new_with_rack 根据网上的例子,做了一个测试程序。 C# 操作Kafka_c# kafka_Riven Chen的博客-CSDN博客 但是执行下面一行时,弹出上面的异常,闪退。 consumer.Subscribe(queueName) 解决方案&…

攻防世界-supersqli

原题 解题思路 直接查找看不到明显的回显变化 先找回显变化数量 -1 order by 2 #如果是3列就报错,说明只有两列。接下来找数据库名称: -1 union select 1,databases # 结果是后端做了一些简单的过滤,需要更换查找语句。 -1; show …

sNMFcross-entropyK

0.简单介绍 稀疏非负矩阵(sNMF)和最小二乘优化来产生祖先比例估计数的祖先推断算法,这个算法呢与admixture来说差别不是很大,但是优点就是快,运算速度可以快到10-30倍左右。 1.安装 这一步不必多说,下载…

PHP加密与安全的最佳实践

PHP加密与安全的最佳实践 概述 在当今信息时代,数据安全是非常重要的。对于开发人员而言,掌握加密和安全的最佳实践是必不可少的。PHP作为一种常用的后端开发语言,提供了许多功能强大且易于使用的加密和安全性相关函数和类。本文将介绍一些P…

C# WPF ListBox 动态显示图片

前言 最近在和其他软件联合做一个本地图片选择传输功能,为此希望图片能够有序的呈现在客户端,简单的实现了一下功能,通过Mvvm模式进行呈现,过程简单通俗,话不多说直接上图。 处理过程 前台代码 你只需要粘贴到你的前台…

c#设计模式-结构型模式 之 桥接模式

前言 桥接模式是一种设计模式,它将抽象与实现分离,使它们可以独立变化。这种模式涉及到一个接口作为桥梁,使实体类的功能独立于接口实现类。这两种类型的类可以结构化改变而互不影响。 桥接模式的主要目的是通过将实现和抽象分离,…

css学习2(利用id与class修改元素)

1、id选择器可以为标有特定id的html元素指定特定的样式。 2、选择器以#开头,后跟某id的属性值。 3、class选择器用于描述一组元素的样式,class可以在多个元素使用。 4、类选择器用.选择。 5、指定特定的元素使用class。 6、元素的多个类用空格分开&…

SpringCloud学习笔记(一)_快速入门

SpringCloud简介 Spring Cloud为开发人员提供了快速构建分布式系统中一些常见模式的工具(例如配置管理,服务发现,断路器,智能路由,微代理,控制总线)。分布式系统的协调导致了样板模式, 使用Spr…

【React】生命周期和钩子函数

概念 组件从被创建到挂载到页面中运行,再到组件不用时卸载的过程。 只有类组件才有生命周期。 分为三个阶段: 挂载阶段更新阶段销毁阶段 三个阶段 挂载阶段 钩子函数 - constructor 创建阶段触发 作用:创建数据 之前定义状态是简写&…

Linux面试笔试题(5)

79、下列工具中可以直接连接mysql的工具有【c 】。 A.xhsell B.plsql C.navicat D.以上都不是 Navicat 是一套可创建多个连接的数据库开发工具, 让你从单一应用程序中同时连接 MySQL、Redis、MariaDB、MongoDB、 SQL Server、Oracle、PostgreSQL和 SQLite 。它与…

【算法日志】贪心算法刷题:重叠区问题(day31)

代码随想录刷题60Day 目录 前言 无重叠区间&#xff08;筛选区间&#xff09; 划分字母区间&#xff08;切割区间&#xff09; 合并区间 前言 今日的重点是掌握重叠区问题。 无重叠区间&#xff08;筛选区间&#xff09; int eraseOverlapIntervals(vector<vector<in…