草庐IT

Unet++语义分割网络(网络结构分析+代码分析)

NukaCC 2023-09-27 原文

1. 前言

许多初入视觉深度学习的小伙伴都会以图像分类网络作为入门案例来学习,个人觉得语义分割网络可以作为分类网络之后第二个学习的案例,因为其网络结构一般较为简单,只要对每个像素点进行分类即可。刚好课题组召开分享会,就和大家分享下Unet++语义分割网络。注:以下分享的许多地方是我的个人理解,可能有不恰当之处还请指出和包涵。视频和代码链接在下方。

视频分享链接:课题组技术分享会-Unet++网络_哔哩哔哩_bilibilihttps://www.bilibili.com/video/BV1La411U7FS/?vd_source=73870594793a8be3d80e0be8a37582d3

github源码:GitHub - MrGiovanni/UNetPlusPlus: Official Keras Implementation for UNet++ in IEEE Transactions on Medical Imaging and DLMIA 2018https://github.com/MrGiovanni/UNetPlusPlus

2. 网络结构和思想

2.1 什么是语义分割

首先明白什么是语义分割,语义分割是对同一种类的物体进行提取,以掩码图的形式输出分割的结果。相比实例分割,它只能提取一个种类,而不能在同一个类中区分出不同的个体。可以简单理解为:实例分割=语义分割+目标检测。

2.2 传统语义分割

下图为一种非常经典的语义分割网络,backbone提取完特征,通过反卷积变回原图尺寸,然后对每个像素点分类,输出结果。

2.3 进阶语义分割

下图为进阶的语义分割,主要不同之处在于会将不同尺寸不同阶段的特征图进行融合,提升分割效果。

那么问题来了,为什么要多个特征图融合呢?原因在于卷积网络的浅层提供了纹理特征,深层提供了丰富的语义信息,两者都有用。拿下面ppt的问题类比一下,假设目前给你提供一个信息,一个目标有鼻子、 眼睛、耳朵、四肢,该目标最大可能性是什么?

有人可能会回答是人,但正如下面ppt所示,事实情况也可能是猩猩或者猴子或者其他小动物。我们不能判断的原因在于只用了语义信息而没用纹理信息。

 2.4 Unet++特性

上面提到了特征跨阶段融合的意义,接下去就不难理解UNet++网络结构为什么要这样做了。UNet++通过短连接和上下采样等操作,间接融合了多个不同层次的特征,而非简单的Encoder与Decoder同层级特征的简单拼接。从其网络特征来看,就像织了一张网一样,将特征融合做到了极致,用专业的术语来说就是稠密连接

 3. 代码讲解

代码讲解在视频里面,视频已经发布,在如下链接里。视频是课题组分享会录制的,里面不仅有Unet++网络结构的讲解,还有很多通用的pytorch代码讲解,创作不易,欢迎一键三连噢(●'◡'●)。注:视频里的代码是其他up主提供的注释版。

课题组技术分享会-Unet++网络_哔哩哔哩_bilibilihttps://www.bilibili.com/video/BV1La411U7FS/?vd_source=73870594793a8be3d80e0be8a37582d3

4. 总结

Unet++是一个非常经典又易于学习的网络,非常值得前期研究一下。

有关Unet++语义分割网络(网络结构分析+代码分析)的更多相关文章

  1. ruby - 使用 ruby​​ 将 HTML 转换为纯文本并维护结构/格式 - 2

    我想将html转换为纯文本。不过,我不想只删除标签,我想智能地保留尽可能多的格式。为插入换行符标签,检测段落并格式化它们等。输入非常简单,通常是格式良好的html(不是整个文档,只是一堆内容,通常没有anchor或图像)。我可以将几个正则表达式放在一起,让我达到80%,但我认为可能有一些现有的解决方案更智能。 最佳答案 首先,不要尝试为此使用正则表达式。很有可能你会想出一个脆弱/脆弱的解决方案,它会随着HTML的变化而崩溃,或者很难管理和维护。您可以使用Nokogiri快速解析HTML并提取文本:require'nokogiri'h

  2. ruby - 如何在 buildr 项目中使用 Ruby 代码? - 2

    如何在buildr项目中使用Ruby?我在很多不同的项目中使用过Ruby、JRuby、Java和Clojure。我目前正在使用我的标准Ruby开发一个模拟应用程序,我想尝试使用Clojure后端(我确实喜欢功能代码)以及JRubygui和测试套件。我还可以看到在未来的不同项目中使用Scala作为后端。我想我要为我的项目尝试一下buildr(http://buildr.apache.org/),但我注意到buildr似乎没有设置为在项目中使用JRuby代码本身!这看起来有点傻,因为该工具旨在统一通用的JVM语言并且是在ruby中构建的。除了将输出的jar包含在一个独特的、仅限ruby​​

  3. ruby-on-rails - Rails 源代码 : initialize hash in a weird way? - 2

    在rails源中:https://github.com/rails/rails/blob/master/activesupport/lib/active_support/lazy_load_hooks.rb可以看到以下内容@load_hooks=Hash.new{|h,k|h[k]=[]}在IRB中,它只是初始化一个空哈希。和做有什么区别@load_hooks=Hash.new 最佳答案 查看rubydocumentationforHashnew→new_hashclicktotogglesourcenew(obj)→new_has

  4. ruby-on-rails - 浏览 Ruby 源代码 - 2

    我的主要目标是能够完全理解我正在使用的库/gem。我尝试在Github上从头到尾阅读源代码,但这真的很难。我认为更有趣、更温和的踏脚石就是在使用时阅读每个库/gem方法的源代码。例如,我想知道RubyonRails中的redirect_to方法是如何工作的:如何查找redirect_to方法的源代码?我知道在pry中我可以执行类似show-methodmethod的操作,但我如何才能对Rails框架中的方法执行此操作?您对我如何更好地理解Gem及其API有什么建议吗?仅仅阅读源代码似乎真的很难,尤其是对于框架。谢谢! 最佳答案 Ru

  5. ruby - 模块嵌套代码风格偏好 - 2

    我的假设是moduleAmoduleBendend和moduleA::Bend是一样的。我能够从thisblog找到解决方案,thisSOthread和andthisSOthread.为什么以及什么时候应该更喜欢紧凑语法A::B而不是另一个,因为它显然有一个缺点?我有一种直觉,它可能与性能有关,因为在更多命名空间中查找常量需要更多计算。但是我无法通过对普通类进行基准测试来验证这一点。 最佳答案 这两种写作方法经常被混淆。首先要说的是,据我所知,没有可衡量的性能差异。(在下面的书面示例中不断查找)最明显的区别,可能也是最著名的,是你的

  6. ruby - 寻找通过阅读代码确定编程语言的ruby gem? - 2

    几个月前,我读了一篇关于ruby​​gem的博客文章,它可以通过阅读代码本身来确定编程语言。对于我的生活,我不记得博客或gem的名称。谷歌搜索“ruby编程语言猜测”及其变体也无济于事。有人碰巧知道相关gem的名称吗? 最佳答案 是这个吗:http://github.com/chrislo/sourceclassifier/tree/master 关于ruby-寻找通过阅读代码确定编程语言的rubygem?,我们在StackOverflow上找到一个类似的问题:

  7. ruby - 用 Ruby 编写一个简单的网络服务器 - 2

    我想在Ruby中创建一个用于开发目的的极其简单的Web服务器(不,不想使用现成的解决方案)。代码如下:#!/usr/bin/rubyrequire'socket'server=TCPServer.new('127.0.0.1',8080)whileconnection=server.acceptheaders=[]length=0whileline=connection.getsheaders想法是从命令行运行这个脚本,提供另一个脚本,它将在其标准输入上获取请求,并在其标准输出上返回完整的响应。到目前为止一切顺利,但事实证明这真的很脆弱,因为它在第二个请求上中断并出现错误:/usr/b

  8. ruby - Net::HTTP 获取源代码和状态 - 2

    我目前正在使用以下方法获取页面的源代码:Net::HTTP.get(URI.parse(page.url))我还想获取HTTP状态,而无需发出第二个请求。有没有办法用另一种方法做到这一点?我一直在查看文档,但似乎找不到我要找的东西。 最佳答案 在我看来,除非您需要一些真正的低级访问或控制,否则最好使用Ruby的内置Open::URI模块:require'open-uri'io=open('http://www.example.org/')#=>#body=io.read[0,50]#=>"["200","OK"]io.base_ur

  9. ruby - 是否有用于序列化和反序列化各种格式的对象层次结构的模式? - 2

    给定一个复杂的对象层次结构,幸运的是它不包含循环引用,我如何实现支持各种格式的序列化?我不是来讨论实际实现的。相反,我正在寻找可能会派上用场的设计模式提示。更准确地说:我正在使用Ruby,我想解析XML和JSON数据以构建复杂的对象层次结构。此外,应该可以将该层次结构序列化为JSON、XML和可能的HTML。我可以为此使用Builder模式吗?在任何提到的情况下,我都有某种结构化数据-无论是在内存中还是文本中-我想用它来构建其他东西。我认为将序列化逻辑与实际业务逻辑分开会很好,这样我以后就可以轻松支持多种XML格式。 最佳答案 我最

  10. 程序员如何提高代码能力? - 2

    前言作为一名程序员,自己的本质工作就是做程序开发,那么程序开发的时候最直接的体现就是代码,检验一个程序员技术水平的一个核心环节就是开发时候的代码能力。众所周知,程序开发的水平提升是一个循序渐进的过程,每一位程序员都是从“菜鸟”变成“大神”的,所以程序员在程序开发过程中的代码能力也是根据平时开发中的业务实践来积累和提升的。提高代码能力核心要素程序员要想提高自身代码能力,尤其是新晋程序员的代码能力有很大的提升空间的时候,需要针对性的去提高自己的代码能力。提高代码能力其实有几个比较关键的点,只要把握住这些方面,就能很好的、快速的提高自己的一部分代码能力。1、多去阅读开源项目,如有机会可以亲自参与开源

随机推荐