【小样本分割 2022 ECCV】SSP

news2024/12/23 4:29:49

文章目录

  • 【小样本分割 2022 ECCV】SSP
    • 摘要
    • 1. 介绍
    • 2. 相关工作
    • 3. 自支持小样本语义分割
      • 3.1 动机
      • 3.2 自支持原型-SSM
      • 3.3 自适应自支持背景原型-ASBP
      • 3.4 自支持匹配-SSL
    • 3. 代码

【小样本分割 2022 ECCV】SSP

论文题目:Self-Support Few-Shot Semantic Segmentation

中文题目:自支持小样本语义分割

论文链接:https://arxiv.org/abs/2207.11549

论文代码:https://github.com/fanq15/ssp

论文团队:香港科学技术大学&哈尔滨工业大学&快手科技

发表时间:2022年7月

DOI:

引用:Fan Q, Pei W, Tai Y W, et al. Self-support few-shot semantic segmentation[C]//Computer Vision–ECCV 2022: 17th European Conference, Tel Aviv, Israel, October 23–27, 2022, Proceedings, Part XIX. Cham: Springer Nature Switzerland, 2022: 701-719.

引用数:10【截止时间:2023年5月1号】

摘要

现有的基于支持-查询匹配框架的小样本分割方法取得了很大的进展。 但是他们仍然严重地受到了来自少量支持的类内变化的有限覆盖的影响。

基于简单格式塔原理,即同一对象的像素比同一类不同对象的像素更相似,我们提出了一种新的自支持匹配策略,

该策略使用查询原型来匹配查询特征,其中查询原型是从高置信度的查询预测中收集的。

该策略能够有效地捕获查询对象的一致底层特征,从而匹配查询特征。 提出了自适应的自支撑背景原型生成模块和自支撑损失,进一步方便了自支撑匹配过程。

我们的自支持网络大大提高了原型的质量,从更强的骨干和更多的支持中受益于更多的改进,并在多个数据集上实现了SOTA。

现有的一些小样本分割方法在支持-查询匹配框架的基础上取得了很大的进展。

  • 存在的问题 : support和query同类目标之间存在的外观差异
  • 动机 : 基于简单格式塔原理,即属于同一目标的像素比属于同—类的不同目标的像素更相似。
  • 本文贡献:
    • 提出了一种新的自支持匹配策略,该策略使用查询原型来匹配查询特征,其中查询原型是从高
      置信度查询预测中收集的。该策略可以有效地捕获查询目标的一致基本特征,从而匹配查询特征。
    • 还提出了自适应自支持背景原型生成模块自支持损失,以进一步促进自支持匹配过程。本文
      自支持网络大大提高了原型质量,在多个数据集上实现了SOTA。

1. 介绍

语义分割已经在深度学习网络[29,42,34]和大规模数据集[15,5,93]中取得了显著的进展。 然而,目前高性能的语义分割方法严重依赖于费力的像素级标注,这加速了近年来小样本语义分割(FSS)的发展。

小样本语义分割的目的是只使用少量支持样本来分割任意新的类。 困难在于支持图像是有限的和固定的(通常每个类支持{1,3,5,10}),而查询图像可能是大量的和任意的。

无论支持质量如何,有限的支持图像很容易无法覆盖查询图像中目标类的潜在外观变化。 这显然是由固有的数据稀缺性和多样性造成的,这是小样本学习中两个长期存在的问题。


现有的方法试图通过充分利用有限的支持来解决这一问题,如提出更好的匹配机制生成具有代表性的原型。 尽管它们取得了成功,但仍然不能从根本上解决有限镜头支撑下的外观差异问题。

但是这些方法都无法从根本上解决 support 和 query 之间的 appearance gap 问题。因为它们还都局限在利用非常少数的 support 去分割无穷的 query。


我们提出了一种新的自支持匹配策略来缩小匹配外观差异。 这种策略使用查询原型来匹配查询特性,或者换句话说,使用查询特性来自我支持。 因此,由于查询原型的自匹配特性,我们将其称为自支持原型。 这个新想法的动机是经典格式塔定律,即属于同一物体的像素比属于不同物体的像素更相似


请参阅图1,以获得对我们新颖的自我支持匹配的高级理解。 首先,通过直接匹配支持原型和查询特征生成初始掩码预测。 在初始查询掩码的基础上,收集可信的查询特征生成自支持原型,用于与查询特征进行匹配。 我们的自我支持模块(SSM)收集猫头的可靠特征,用于分割整个黑猫。 我们的模型在基类上进行了优化,以检索由对象片段支持的其他对象部分,即自支持原型。


我们将我们的自支持模块应用于前景和背景原型中进行自支持匹配。 虽然SSM直接有利于前景原型,但请注意,背景通常是杂乱的,这不具有所有背景像素之间共享的全局语义共同性。

因此,我们不是通过聚集所有背景像素来生成全局背景原型,而是通过动态聚集查询图像中相似的背景像素来自适应地为每个查询像素生成自我支持的背景原型。

自适应支持背景原型(ASBP)是由独立的背景区域具有局部语义相似性这一事实所驱动的。 最后,我们提出了一个自支撑损失(SSL)来进一步方便自支撑程序。


因此,我们的自支持匹配策略与传统的支持-查询匹配有根本的不同。 采用灵活的自支持原型进行查询特征匹配,可以有效地捕捉查询对象的一致底层特征,从而实现对查询特征的匹配。 如图1所示,查询和支持图像中的猫在颜色、部位和尺度上都有很大差异,加菲猫支持图像与黑猫查询图像有很大的外观差异,传统的支持-查询匹配无疑会产生较差的分割。 在我们的自支持匹配中,我们的自支持原型(黑猫头部)与查询(整个黑猫)更加一致,因此我们的方法得到了令人满意的结果。


我们是第一个在查询原型和查询特征之间执行自我支持匹配的。 如图1所示,我们的自支撑匹配从根本上不同于常规匹配。 其他方法从额外的未标记图像(PPNET[57]和MLC[82])中学习用于支持查询匹配的更好的支持原型,或者基于支持图像构建各种支持原型生成模块[71,45,81]或特征先验(PFENET[73])。 虽然Panet[75]和CRNET[55]也探索了查询原型,但它们使用查询原型来匹配支持特征,仅作为辅助训练的查询-支持匹配,不能解决外观差异问题。

我们的自支持方法通过缓解类内外观差异问题显著提高了原型质量,在我们的实验验证中,在多个数据集上的性能提升证明了这一点。 尽管思想简单,但我们的自支持方法非常有效,具有多种优点,如更强的主干和更多的支持,产生高置信度的预测,对弱支持标签的鲁棒性更强,对其他方法的泛化程度更高,运行效率更高。 我们将用深入的实验来证实这些优点。 概括地说,我们的贡献是:

  • 提出了一种新的自支持匹配方法,并构造了一种新的自支持网络来解决FSS中的外观差异问题。
  • 我们提出了自我支持原型,自适应自我支持背景原型和自我支持损失,以方便我们的自我支持方法。
  • 我们的自我支持方法从更强大的骨干和更多的支持中受益更多的改进,并在多个数据集上优于以前的SOTA,具有许多可取的优势。

image-20230501223046377

左图说明了我们自支持匹配的核心思想。利用初始查询掩码预测在高置信度区域收集查询特征,然后利用生成的查询原型与查询特征进行自匹配

右上方的图像说明了我们自我支持匹配的动机:相同对象的像素/区域比来自不同对象的像素/区域更相似。 方框中的数字表示两个物体之间的余弦相似度。

右下角的图像说明了我们的自我支持匹配与传统的匹配方法有根本的不同。

语义分割在深度学习网络和大规模数据集方面取得了显著进展。但是当前高性能语义分割方法严重依赖于费力的像素级标注,加速了小样本语义分割(FSS)的发展。

FSS的问题: 固有的数据稀少性和数据多样性

  • 数据稀少性是指支持图像很少,每个新类别只有不到10个样本。
  • 数据多样性是指查询图像可能是海量和任意的。

支持图像中物体根本无法涵盖所有查询图像中同类别物体。

2. 相关工作

语义分割。

语义分割是计算机视觉的一个基本任务,用于产生像素级的稠密语义预测。 端到端的全卷积网络(FCN)[58]极大地推进了这一技术的发展。 随后的工作遵循了FCN范式,并贡献了许多有效的模块来进一步提高性能,如编码器-解码器体系结构[4,13,11,67]、图像和特征金字塔模块[39,91,10,49,50]、上下文聚合模块[25,26,33,92,95,36,85,89]和高级卷积层[84,9,14,63]。 尽管如此,上述分割方法在很大程度上依赖于丰富的像素级标注。 本文旨在解决少镜头场景下的语义分割问题。

小样本学习。

小样本学习的目标是从很少的样本中识别新的概念。 在过去的几年里,这种低成本的财产吸引了许多研究兴趣。 主要有三种方法。 第一种是迁移学习方法[12,28,16,65],通过在两个阶段的优化过程中将从基类学习到的先验知识调整到新的类。 第二种是基于优化的方法[24,6,44,30,43,2,31,68],它通过从少量样本中元学习优化过程来快速更新模型。 最后是基于度量的方法[1,17,35,40,46,47],它在支持查询对上应用暹罗网络[40]来学习评估它们相关性的一般度量。 我们的工作,包括许多关于各种高级计算机视觉任务的少量工作[23,37,90,80,22]都受到了基于度量的方法的启发。

小样本语义分割。

小样本语义分割是Shaban等人首创的。 [69]。 后来的工作主要采用了基于度量的主流范式[18],并进行了各种改进,例如用各种注意机制[70,54,83]、更好的优化[94,53]、存储模块[77,79]、图神经网络[78,74,87]、基于学习的分类器[72,59]、渐进匹配[32,96]或其他高级技术[86,52,61,48]改进支持查询图像之间的匹配过程。 我们是第一个在查询原型和查询特征之间执行自我支持匹配的。 我们的自支持匹配方法也与原型生成方法有关。 有些方法利用额外的未标记数据[82,57]或特征先验信息[73]来进一步增强特征。 其他方法使用各种技术生成代表性支持原型,例如,注意机制[88,27]、自适应原型学习[71,45,64]或各种原型生成方法[62,81]。 尽管查询原型已经在一些方法中得到了探索[75,55],但它们只使用查询原型来匹配支持特征以进行原型正则化。 最后,现有方法在支持-查询匹配中存在类内差异问题。 另一方面,我们提出了一种新的自我支持匹配策略来有效地解决这个匹配问题。

3. 自支持小样本语义分割

在只有少量支持图像的情况下,小样本语义分割的目的是利用从基类中推广的模型来分割新类的对象。 现有主流的少镜头语义分割方案可表述为:输入支持和查询图像 { I s , I q } \left\{I_{s},I_{q}\right\} {Is,Iq}通过权重共享主干处理,提取图像特征 { F s , F q } ∈ R C × H × W , \{\mathcal{F}_{s},\mathcal{F}_{q}\}\in\mathbb{R}^{C\times H\times W}, {Fs,Fq}RC×H×W,,其中C为通道大小,H×W为特征空间大小。 然后将支持度特征 F s \mathcal{F}_{s} Fs及其地真掩码 M s {\mathcal{M}}_{s} Ms送入掩码平均池层,分别生成前景和背景区域的支持度原型向量 P s = { P s , f , P s , b } ∈ R C × 1 × 1 \mathcal{P}_{s}=\{\mathcal{P}_{s,f},\mathcal{P}_{s,b}\}\in \mathbb{R}^{C\times 1 \times 1} Ps={Ps,f,Ps,b}RC×1×1。 最后,通过计算 P s {\mathcal{P}}_{s} Ps F q {\mathcal{F}}_{q} Fq之间的余弦相似度,生成两个距离映射 D = { D f , D b } \mathcal{D}=\{\mathcal{D}_{f},\mathcal{D}_{b}\} D={Df,Db},然后通过Softmax运算处理,作为最终预测 M 1 = s o f t m a x ( D ) \mathcal{M}_{1}=\mathrm{softmax}(\mathcal{D}) M1=softmax(D)

3.1 动机

目前的FSS方法很大程度上依赖于支持原型来分割查询对象,通过将每个查询像素与支持原型进行密集匹配。 然而,这种跨对象匹配严重地受到类内外观差异的影响,即使属于同一类,支持和查询中的对象看起来也可能非常不同。 如此高的类内变化不能仅通过少数支持来协调,因此由于查询和支持之间的外观差距很大,导致匹配结果很差。

为了验证格式塔定律在缩小这种外观差异方面的相关性,我们统计分析了Pascal VOC中跨对象和内对象像素的特征余弦相似性,其中像素特征是从ImageNet-Pretrianed Resnet-50中提取的。 表1显示,属于同一对象的像素比跨对象的像素相似得多。 值得注意的是,背景像素本身具有相似的特征,其中图像内背景像素比图像间背景像素更相似。

image-20230410150359010

因此,我们建议利用查询特性来生成自我支持的原型,以匹配查询特性本身。 值得注意的是,这样的原型沿着同源的查询特征对齐查询,从而可以显著地缩小支持和查询之间的特征差距。 事后看来,自支持匹配优于传统支持查询匹配的关键原因在于,对于给定的可视对象类,对象内相似度远高于对象间相似度。

3.2 自支持原型-SSM

image-20230410145821180

图 2. 整体自立网络架构。 我们首先使用传统的基于支持原型的匹配网络生成初始掩码预测。 然后利用初始查询掩码聚合查询特征生成自支持原型,即自支持前台原型(SSFP)和自适应自支持后台原型(ASBP)。 最后,我们结合支持原型和自支持原型来执行与查询特征的匹配。

我们的核心思想(图2)是聚合查询特性来生成查询原型,并使用它来自我支持查询特性本身。

概括地说,常规的支持原型生成过程是:
P s = M A P ( M s , F s ) , {\cal P}_{s}=M A P({\cal M}_{s},{\cal F}_{s}), Ps=MAP(Ms,Fs),
其中 M A P MAP MAP是屏蔽平均池操作,用于生成具有查询特征 F q \mathcal{F}_q Fq的匹配预测:
M 1 = s o f t m a x ( c o s i n e ( P s , F q ) ) , \mathcal{M}_1=\mathrm{softmax}(\mathrm{cosine}(\mathcal{P}_s,\mathcal{F}_q)), M1=softmax(cosine(Ps,Fq)),
其中余弦是余弦相似性度量。

现在,我们可以用同样的方式生成查询原型 P q \mathcal{P}_{q} Pq,只是查询图像 M q \mathcal{M}_{q} Mq的真值掩码在推理过程中不可用。 因此,我们需要使用预测查询掩码 M ~ q \widetilde{\mathcal{M}}_q M q来聚合查询特征。 查询原型生成过程可以表述为:
P q = M A P ( M ~ q , F q ) , \mathcal{P}_{q}=M A P(\widetilde{\mathcal{M}}_{q},\mathcal{F}_{q}), Pq=MAP(M q,Fq),
其中 M ~ q = 1 ( M 1 > τ ) \widetilde{\mathcal{M}}_{q}=\mathbb{1}(\mathcal{M}_{1}>\tau) M q=1(M1>τ) M 1 \mathcal M_1 M1是由公式2生成的估计查询掩码,1是指示函数。

利用掩码阈值 τ \tau τ来控制查询特征的采样范围,前台和后台的查询掩码分别设置为 { τ f g = 0.7 , τ b g = 0.6 } \{\tau_{f g}=0.7,\tau_{b g}=0.6\} {τfg=0.7,τbg=0.6}。 估计的自支持原型 P q = { P q , f , P q , b } {\cal P}_{q}=\{{\cal P}_{q,f},{\cal P}_{q,b}\} Pq={Pq,f,Pq,b}将用于匹配查询特征。

我们理解读者对自支撑原型质量的天然关注,这是基于估计的查询掩码生成的,即估计的掩码是否能够有效地自支撑原型生成。我们发现即使是估计的查询掩码也不完美,只要它覆盖了一些有代表性的对象片段,就足以检索同一对象的其他区域。为了验证部分对象或对象片段能够支持整个对象,我们使用部分原型训练和评估模型,这些原型是根据真实掩码标签从随机选择的特征中聚合而来的。我们使用 ResNet-50 骨干在 Pascal VOC 数据集上进行了 1-shot 分割实验。如表 2 所示,在减少原型生成的聚合对象区域的同时,我们的自支撑原型始终实现高分割性能。相比之下,传统的支持原型始终获得低劣的性能,即使使用整个对象的完美支持功能。

image-20230410150228304

通过随机选择非目标区域的图像特征,并将这些特征聚合到上述部分原型中,在部分原型中引入20%噪声比的噪声特征,以模拟推理过程中真实的自我支持生成。 令我们惊喜的是,在这样嘈杂的环境中,我们的自助式样机仍然比传统的支持式样机工作得好得多。 注意,每个图像可能包含多个对象,因此良好的性能表明我们的自支持原型也可以很好地处理多对象场景。 这些结果证实了我们的自支撑样机在实际应用中的实用性和优越性。

3.3 自适应自支持背景原型-ASBP

前景像素具有语义共性,这构成了我们在查询特征和前景对象支持原型之间自动支持原型生成和匹配过程的基本原理。 因此,我们可以利用屏蔽平均池来生成自我支持的前景原型(图3(a)):

P q , f = M A P ( M ~ q , f , F q ) , \mathcal{P}_{q,f}=MAP(\widetilde{\mathcal{M}}_{q,f},\mathcal{F}_q), Pq,f=MAP(M q,f,Fq),
其中 M ~ q , f \widetilde{\mathcal{M}}_{q,f} M q,f是前面提到的估计查询掩码。

另一方面,背景可能是杂乱的,在不相交的区域中,共性可以被简化为局部语义相似性,而不是所有背景像素之间共享的全局语义共性。 例如,对于一个以狗为目标类的查询图像,人和车等其他对象都被视为背景,但它们在外观和语义层次上都是不同的。 如表1所示,与前景像素相比,背景像素相似性更小,这也验证了这一观察,尤其是在对象/图像内的情况下。 这促使我们为不同的查询语义区域生成多个自支持背景原型。

一个简单的解决方案是使用聚类算法直接对多个背景原型进行分组,然后在每个查询像素处选择最相似的原型进行背景匹配。 这种显式背景分组在很大程度上依赖于聚类算法,该算法不稳定且耗时。 因此,我们提出了一种更加灵活高效的方法,为每个查询像素自适应地生成自我支持的背景原型(图3(b))。

其思想是为每个查询像素动态聚合相似的背景像素,以生成自适应的自我支持背景原型

具体来说,我们首先通过对查询特征 F q \mathcal{F}_q Fq与背景掩码 M ~ q , b \widetilde{\mathcal{M}}_{q,b} M q,b进行掩码乘法来收集背景查询特征 F q , b ∈ R C × M \mathcal{F}_{q,b}\in\mathbb{R}^{C\times M} Fq,bRC×M,其中 M M M是背景区域的像素个数。 然后我们可以通过矩阵乘法运算 M a t m u l Matmul Matmul生成重塑后的背景查询特征 F q , b \mathcal{F}_{q,b} Fq,b和全查询特征 F q \mathcal{F}_q Fq的像素之间的亲和力矩阵 A \mathcal{A} A
A = M a t M u l ( F q , b T , F q ) , \mathcal{A}=Mat Mul({\mathcal{F}_{q,b}}^T,\mathcal{F}_q), A=MatMul(Fq,bT,Fq),
其中 A \mathcal{A} A的大小为 R M × ( H × W ) \mathbb{R}^{M \times (H \times W)} RM×(H×W)。 在第一维上通过Softmax运算对亲和力矩阵进行归一化,并对每个查询像素的背景查询特征进行加权聚合,生成自适应自支持背景原型 P q , b ⋆ ∈ R C × H × W \mathcal{P}_{q,b}^{\star}\in\mathbb{R}^{C\times H\times W} Pq,bRC×H×W
P q , b ⋆ = M a t M u l ( F q , b , s o f t m a x ( A ) ) . \mathcal{P}_{q,b}^{\star}=M a t\mathop{M u l}(\mathcal{F}_{q,b},\mathrm{softmax}(\mathcal{A})). Pq,b=MatMul(Fq,b,softmax(A)).
用自适应的自支持背景原型更新自支持原型: P q = { P q , f , P q , b ⋆ } . \mathcal{P}_{q}=\{\mathcal{P}_{q,f},\mathcal{P}_{q,b}^{\star}\}. Pq={Pq,f,Pq,b}.

image-20230502101505008

原型生成

(a)自我支持(SS)前景原型

(b)自适应自我支持背景原型。

3.4 自支持匹配-SSL

我们加权组合了支持原型 P s \mathcal{P}_s Ps和自我支持原型 P q \mathcal{P}_q Pq

P s ⋆ = α 1 P s + α 2 P q , \mathcal{P}_s^\star=\alpha_1\mathcal{P}_s+\alpha_2\mathcal{P}_q, Ps=α1Ps+α2Pq,
其中, α 1 \alpha_1 α1 α 2 \alpha_2 α2是调谐权重,我们在实验中设置 α 1 = α 2 = 0.5 \alpha_1=\alpha_2=0.5 α1=α2=0.5。 然后我们计算增强支持度原型 P s ⋆ \mathcal{P}_s^\star Ps和查询特征 F q \mathcal{F}_q Fq之间的余弦距离来生成最终的匹配预测:
M 2 = s o f t m a x ( c o s i n e ( P s ⋆ , F q ) ) . \mathcal{M}_{2}=\mathrm{softmax}(\mathrm{cosine}(\mathcal{P}_{s}^{\star},\mathcal{F}_{q})). M2=softmax(cosine(Ps,Fq)).
然后我们在生成的距离进行有监督训练监督:
L m = B C E ( cosine ⁡ ( P s ⋆ , F q ) , G q ) , \mathcal{L}_m=BCE(\operatorname{cosine}(\mathcal{P}_s^{\star},\mathcal{F}_q),\mathcal{G}_q), Lm=BCE(cosine(Ps,Fq),Gq),
其中 B C E BCE BCE是二值交叉熵损失, G q \mathcal{G}_q Gq是查询图像的真值掩码。

为了进一步简化自支持匹配过程,我们提出了一种新的查询自支持丢失。 对于查询特性 F q \mathcal{F}_q Fq及其原型 P q \mathcal{P}_{q} Pq,我们应用以下训练监督:
L q = B C E ( cosine ⁡ ( P q , F q ) , G q ) . \mathcal L_q=BCE(\operatorname{cosine}(\mathcal P_q,\mathcal F_q),\mathcal G_q). Lq=BCE(cosine(Pq,Fq),Gq).
我们可以在支持度特征上应用同样的过程来引入支持度自匹配损失 L s \mathcal{L}_s Ls

最后,我们通过联合优化前述所有损失,以端到端的方式训练模型:
L = λ 1 L m + λ 2 L q + λ 3 L s , \mathcal{L}=\lambda_1\mathcal{L}_m+\lambda_2\mathcal{L}_q+\lambda_3\mathcal{L}_s, L=λ1Lm+λ2Lq+λ3Ls,
其中λ1=1.0,λ2=1.0,λ3=0.2是损失权重。

3. 代码

原生代码写的非常的不错。我这里做了注释。

from .resnet import resnet50, resnet101

import torch
from torch import nn
import torch.nn.functional as F


class SSP_MatchingNet(nn.Module):
    def __init__(self, backbone, pretrained=True, refine=False):
        super(SSP_MatchingNet, self).__init__()
        backbone = eval(backbone)(pretrained=pretrained)  # 创建backbone
        self.layer0 = nn.Sequential(backbone.conv1, backbone.bn1, backbone.relu, backbone.maxpool)
        self.layer1, self.layer2, self.layer3 = backbone.layer1, backbone.layer2, backbone.layer3
        self.refine = refine

    def forward(self, img_s_list, mask_s_list, img_q, mask_q):
        """

        Args:
            img_s_list: support images
                        List   shape=shot x [batch size,3,473,473]
            mask_s_list: masks for support images 
                    List  shape=shot x [batch size,473,473]
            img_q:  query images
                    [batch_size,3,473,473]
            mask_q:  query images
                    [batch_size,473,473]
        """
        h, w = img_q.shape[-2:]

        # feature maps of support images
        feature_s_list = []
        #  获取支持集的特征
        for k in range(len(img_s_list)):
            with torch.no_grad():
                s_0 = self.layer0(img_s_list[k])
                s_0 = self.layer1(s_0)  # [4,256,119,119]
            s_0 = self.layer2(s_0)  # [4,256,119,119]-> [4,256,60,60]
            s_0 = self.layer3(s_0)  # [4,256,60,60] -> [4,1024,60,60]
            feature_s_list.append(s_0)
            del s_0

        # 获取查询集图像的特征
        with torch.no_grad():
            q_0 = self.layer0(img_q)
            q_0 = self.layer1(q_0)
        q_0 = self.layer2(q_0)
        feature_q = self.layer3(q_0)  # [4,1024,60,60]

        # foreground(target class) and background prototypes pooled from K support features
        feature_fg_list = []
        feature_bg_list = []
        supp_out_ls = []
        for k in range(len(img_s_list)):
            # feature_fg=[1,4,1024]
            feature_fg = self.masked_average_pooling(feature_s_list[k], (mask_s_list[k] == 1).float())[None, :]
            # feature_bg=[1,4,1024]
            feature_bg = self.masked_average_pooling(feature_s_list[k], (mask_s_list[k] == 0).float())[None, :]
            feature_fg_list.append(feature_fg)
            feature_bg_list.append(feature_bg)

            if self.training:

                # 自支持损失 SSL
                # [4,60,60] 。支持集图像的原型 来分割 支持集图像
                supp_similarity_fg = F.cosine_similarity(feature_s_list[k], feature_fg.squeeze(0)[..., None, None], dim=1)
                # [4,60,60]
                supp_similarity_bg = F.cosine_similarity(feature_s_list[k], feature_bg.squeeze(0)[..., None, None], dim=1)
                # [4,2,60,60]
                supp_out = torch.cat((supp_similarity_bg[:, None, ...], supp_similarity_fg[:, None, ...]), dim=1) * 10.0
                supp_out = F.interpolate(supp_out, size=(h, w), mode="bilinear", align_corners=True)  # [4,2,473,473]
                supp_out_ls.append(supp_out)

        # 对shot个图片进行平均,计算原型 [4,1024,1,1]
        FP = torch.mean(torch.cat(feature_fg_list, dim=0), dim=0).unsqueeze(-1).unsqueeze(-1)
        # 背景原型 [4,1024,1,1]
        BP = torch.mean(torch.cat(feature_bg_list, dim=0), dim=0).unsqueeze(-1).unsqueeze(-1)

        # 计算查询特征和前景和背景的原型 之间的相似度。计算出初步的分割掩码
        out_0 = self.similarity_func(feature_q, FP, BP)  # [4,2,60,60]

        ##################### Self-Support Prototype (SSP) #####################
        # SSFP_1=[4,1024,1,1],SSBP_1=[4,1024,1,1],ASBP_1=[4,1024,60,60] ,ASFP_1=[4,1024,60,60]
        SSFP_1, SSBP_1, ASFP_1, ASBP_1 = self.SSP_func(feature_q, out_0)  
        
        FP_1 = FP * 0.5 + SSFP_1 * 0.5  # [4,1024,1,1]
        BP_1 = SSBP_1 * 0.3 + ASBP_1 * 0.7  # [4,1024,1,1]

        out_1 = self.similarity_func(feature_q, FP_1, BP_1)  # [4,2,60,60]

        ##################### SSP Refinement #####################
        if self.refine:
            SSFP_2, SSBP_2, ASFP_2, ASBP_2 = self.SSP_func(feature_q, out_1)

            FP_2 = FP * 0.5 + SSFP_2 * 0.5
            BP_2 = SSBP_2 * 0.3 + ASBP_2 * 0.7

            FP_2 = FP * 0.5 + FP_1 * 0.2 + FP_2 * 0.3
            BP_2 = BP * 0.5 + BP_1 * 0.2 + BP_2 * 0.3

            out_2 = self.similarity_func(feature_q, FP_2, BP_2)

            out_2 = out_2 * 0.7 + out_1 * 0.3

        # out_0 = F.interpolate(out_0, size=(h, w), mode="bilinear", align_corners=True)
        out_1 = F.interpolate(out_1, size=(h, w), mode="bilinear", align_corners=True)  # [4,2,473,473]

        if self.refine:
            out_2 = F.interpolate(out_2, size=(h, w), mode="bilinear", align_corners=True)
            out_ls = [out_2, out_1]
        else:
            out_ls = [out_1]

        if self.training:

            # 自支持损失 SSL
            fg_q = self.masked_average_pooling(feature_q, (mask_q == 1).float())[None, :].squeeze(0)  # [4,1024]
            bg_q = self.masked_average_pooling(feature_q, (mask_q == 0).float())[None, :].squeeze(0)  # [4,1024]

            self_similarity_fg = F.cosine_similarity(feature_q, fg_q[..., None, None], dim=1)  # [4,60,60]
            self_similarity_bg = F.cosine_similarity(feature_q, bg_q[..., None, None], dim=1)  # [4,60,60]
            self_out = torch.cat((self_similarity_bg[:, None, ...], self_similarity_fg[:, None, ...]), dim=1) * 10.0  # [4,2,60,60]

            self_out = F.interpolate(self_out, size=(h, w), mode="bilinear", align_corners=True)
            supp_out = torch.cat(supp_out_ls, 0)

            out_ls.append(self_out)
            out_ls.append(supp_out)

        return out_ls

    def SSP_func(self, feature_q, out):
        """
        查询编码 和 分割结果
        """
        bs = feature_q.shape[0]  # [4,1024,60,60] 查询编码
        pred_1 = out.softmax(1)  # [4,2,60,60]-> [4,2,60,60] 分割结果
        pred_1 = pred_1.view(bs, 2, -1)  # [4,2,3600]
        pred_fg = pred_1[:, 1]  # [4,3600] # 前景分割概率
        pred_bg = pred_1[:, 0]  # [4,3600] # 背景分割概率
        fg_ls = []
        bg_ls = []
        fg_local_ls = []
        bg_local_ls = []
        for epi in range(bs):
            fg_thres = 0.7  # 0.9 #0.6
            bg_thres = 0.6  # 0.6
            cur_feat = feature_q[epi].view(1024, -1)  # [1024,3600] 当前query特征
            f_h, f_w = feature_q[epi].shape[-2:]

            # step 1: 通过对查询特征 与 背景掩码 进行掩码乘法来收集背景查询特征
            if (pred_fg[epi] > fg_thres).sum() > 0:
                fg_feat = cur_feat[:, (pred_fg[epi] > fg_thres)]  # .mean(-1) #选出前景特征
            else:
                fg_feat = cur_feat[:, torch.topk(pred_fg[epi], 12).indices]  # .mean(-1)
            if (pred_bg[epi] > bg_thres).sum() > 0:
                bg_feat = cur_feat[:, (pred_bg[epi] > bg_thres)]  # .mean(-1)
            else:
                bg_feat = cur_feat[:, torch.topk(pred_bg[epi], 12).indices]  # .mean(-1) # 选出背景特征

            # global proto
            fg_proto = fg_feat.mean(-1)  # 高置信度的前景的原型
            bg_proto = bg_feat.mean(-1)  # 高置信度的背景的原型
            fg_ls.append(fg_proto.unsqueeze(0))
            bg_ls.append(bg_proto.unsqueeze(0))

            # local proto
            fg_feat_norm = fg_feat / torch.norm(fg_feat, 2, 0, True)  # 1024, N1 高置信度的前景的特征
            bg_feat_norm = bg_feat / torch.norm(bg_feat, 2, 0, True)  # 1024, N2 高置信度的背景的特征
            cur_feat_norm = cur_feat / torch.norm(cur_feat, 2, 0, True)  # 1024, N3

            cur_feat_norm_t = cur_feat_norm.t()  # N3, 1024

            # step 2: 通过矩阵乘法运算生成亲和力矩阵A
            fg_sim = torch.matmul(cur_feat_norm_t, fg_feat_norm) * 2.0  # N3, N1
            bg_sim = torch.matmul(cur_feat_norm_t, bg_feat_norm) * 2.0  # N3, N2

            # 第一维上通过Softmax运算对亲和力矩阵进行归一化
            fg_sim = fg_sim.softmax(-1)
            bg_sim = bg_sim.softmax(-1)

            # 生产自适应背景原型
            fg_proto_local = torch.matmul(fg_sim, fg_feat.t())  # N3, 1024
            bg_proto_local = torch.matmul(bg_sim, bg_feat.t())  # N3, 1024

            fg_proto_local = fg_proto_local.t().view(1024, f_h, f_w).unsqueeze(0)  # 1024, N3
            bg_proto_local = bg_proto_local.t().view(1024, f_h, f_w).unsqueeze(0)  # 1024, N3

            
            fg_local_ls.append(fg_proto_local)
            bg_local_ls.append(bg_proto_local)

        # global proto
        new_fg = torch.cat(fg_ls, 0).unsqueeze(-1).unsqueeze(-1)
        new_bg = torch.cat(bg_ls, 0).unsqueeze(-1).unsqueeze(-1)

        # local proto
        new_fg_local = torch.cat(fg_local_ls, 0).unsqueeze(-1).unsqueeze(-1)
        new_bg_local = torch.cat(bg_local_ls, 0)

        return new_fg, new_bg, new_fg_local, new_bg_local

    def similarity_func(self, feature_q, fg_proto, bg_proto):
        """
         通过计算相似度来进行分割
         feature_q: [4,1024,60,60] 查询集特征
         fg_proto: [4,1024,1,1] 前景原型
         bg_proto: [4,1024,1,1] 背景原型
         结果: [4,2,60,60] 初步的分割结果
        """

        similarity_fg = F.cosine_similarity(feature_q, fg_proto, dim=1)
        similarity_bg = F.cosine_similarity(feature_q, bg_proto, dim=1)

        out = torch.cat((similarity_bg[:, None, ...], similarity_fg[:, None, ...]), dim=1) * 10.0  # [4,2,60,60]
        return out

    def masked_average_pooling(self, feature, mask):
        """
        通过mask_pool操作获取对应特征的原型。
        feature: [4,1024,60,60]
        mask:  [4,473,473]
        return feature : [4,1024]
        """
        # [4,473,473] -> [4,1,60,60]
        mask = F.interpolate(mask.unsqueeze(1), size=feature.shape[-2:], mode='bilinear', align_corners=True)
        masked_feature = torch.sum(feature * mask, dim=(2, 3)) / (mask.sum(dim=(2, 3)) + 1e-5)
        return masked_feature

ECCV 2022 | SSP: 自支持匹配的小样本任务新思想 - 知乎 (zhihu.com)

(4条消息) 【小样本分割】Self-Support Few-Shot Semantic Segmentation_小样本语义分割_栗子菜菜的博客-CSDN博客

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

SpringCloud 微服务系列——【Gateway、Config组件使用】

✅作者简介:2022年博客新星 第八。热爱国学的Java后端开发者,修心和技术同步精进。 🍎个人主页:Java Fans的博客 🍊个人信条:不迁怒,不贰过。小知识,大智慧。 💞当前专栏…

第二十三章 材质

3D模型主要是通过材质(Material)和贴图(Texture)来表现其精美的外表,说白了就是一张“画皮”而已。我们之前的DirectX课程中介绍过材质,它实际就是对光的反射率,这样简单的设置并不能展现3D模型…

Linux线程 概念、特点、线程间资源共享情况

1. 线程概念 线程是轻量级的进程;Linux中,线程本质上仍是进程。 进程是OS分配资源的最小单位,线程是OS调度的最小单位。 NPTL 当前Linux线程库为redHat开发的NPTL,查看本地线程库版本: getconf GNU_LIBPTHREAD_VE…

【C++】三元操作符、创建并初始化C++对象、C++new关键字

C的三元操作符 if的语法糖 例1 #include <iostream> #include <string>static int s_Level 1; static int s_Speed 2;int main() {if (s_Level > 5){s_Speed 10;}else{s_Speed 5;}std::cin.get(); }用三元操作符&#xff1a; s_Speed s_Level > 5 ?…

基础篇-并发篇

**63.线程状态 添加主线程和子线程 ** 65.线程状态 核心线程和任务队列都是有上限的&#xff0c;所以都满了话就开始使用救急线程; 救急线程也是有上限的&#xff0c;如果再来新的线程的话就需要拒绝策越; 注意&#xff1a;这里不需要等待5000ms&#xff0c;几乎是同时打印 注…

[230503] 2021年托福阅读真题第1篇|Grinding Grain 磨粒

11:21&#xff5e;11:41 慢 20min 正确率&#xff1a;6.5/10 题目来源&#xff1a;链接: https://pan.baidu.com/s/15FYCuD7__slfGvdsBIHgLQ 提取码: iynj --来自百度网盘超级会员v5的分享【内含2021年100篇托福阅读真题】 目录 Grinding Grain 题目 Grinding Grain It now…

2016 ICPC合肥站 传递 HDU-5961(拓扑排序 / bitset / 暴力(可hack))

题目链接&#xff1a;HDU-5961 传递 中文题面就不解释题目意思&#xff0c;解释一下名词的意思 完全图&#xff1a;对于一个无向图 G G G 而言&#xff0c;设点集为 V V V&#xff0c;点集中任意不相同两点 u , v u, v u,v 间都有且仅有一条边叫做完全图。 竞赛图&#xff1…

【玩转Git三剑客笔记】第一章 Git基础

第一章 Git基础 1.综述2.安装Git3.使用Git之前需要做的最小配置4.创建第一个仓库并配置local用户信息1.创建Git仓库2.设置Git最小配置 5.通过几次commit来认识工作区和暂存区1.将工作区中所有已经被git追踪的文件一起添加到暂存区2.git log查看提交日志 6.给文件重命名的简便方…

密码学【java语言】初探究

文章目录 前言一 密码学1.1 古典密码学1.1.1 替换法1.1.2 移位法1.1.3 古典密码破解方式 二 近代密码学2.1 现代密码学2.1.1 散列函数2.1.2 对称密码2.1.3 非对称密码 二 凯撒加密的实践2.1 基础知识&#xff1a;ASCII编码2.2 ascii编码演示2.3 凯撒加密和解密实践2.4 频率分析…

安装Ubuntu22.04虚拟机的一些常见问题解决方法

文章目录 VirttalBox 开启共享剪切板文件夹、拖放的功能VirtualBox 安装 ubuntu后安装增强工具无效的解决办法解决ubuntu您没有权限查看“ 某某文件夹”的内容所需的权限linux更换源的两种方法[如何在 Ubuntu 20.04 上安装 Visual Studio Code - ](https://zhuanlan.zhihu.com/…

【Java入门合集】第二章Java语言基础(二)

【Java入门合集】第二章Java语言基础&#xff08;二&#xff09; 博主&#xff1a;命运之光 专栏JAVA入门 学习目标 掌握变量、常量、表达式的概念&#xff0c;数据类型及变量的定义方法&#xff1b; 掌握常用运算符的使用&#xff1b; 掌握程序的顺序结构、选择结构和循环结构…

权限提升:不带引号服务路径 || 不安全的服务权限.

权限提升&#xff1a;不带引号服务路径 || 不安全的服务权限. 权限提升简称提权&#xff0c;由于操作系统都是多用户操作系统&#xff0c;用户之间都有权限控制&#xff0c;比如通过 Web 漏洞拿到的是 Web 进程的权限&#xff0c;往往 Web 服务都是以一个权限很低的账号启动…

Nature:李龙等揭示抑郁症模型中社交压力阻断社交奖赏的神经环路机制

在人类社会中&#xff0c;社会压力尤其是创伤性社会经历会导致抑郁症、社交焦虑及创伤后应激障碍等多种精神疾病【1】。在抑郁症研究领域&#xff0c;有研究表明社会创伤会损害大脑负责奖赏的脑区功能&#xff0c;使社交活动变得不再有奖赏性&#xff0c;从而导致严重的社交回避…

【ShenYu系列】ShenYu Dubbo插件全流程源码解析

网关启动 在ShenyuConfiguration注入ShenyuWebHandler。 Bean("webHandler")public ShenyuWebHandler shenyuWebHandler(final ObjectProvider<List<ShenyuPlugin>> plugins, final ShenyuConfig config, Lazy final ShenyuLoaderService shenyuLoaderS…

初识Go语言20-包与工程化【用go mod管理工程、包引入规则、init调用链、可见性】

文章目录 包与工程化用go mod管理工程包引入规则init调用链可见性 包与工程化 用go mod管理工程 初始化项目: go mod init $module_name$module_name和目录名可以不一样。上述命令会生成go.mod文件&#xff0c;该文件内容形如&#xff1a; module go-coursego 1.17require (…

HarmonyOS服务卡片开发-文件组织与配置学习

HarmonyOS服务卡片开发-文件组织与配置学习 1.文件组织 目录结构 JS服务卡片(entry/src/main/js/Component)的典型开发目录结构如下&#xff1a; 目录结构中文件分类如下&#xff1a; .hml结尾的HML模板文件&#xff0c;这个文件用来描述卡片页面的模板布局结构。 .css结…

云计算(Cloud Computing)

一、从技术概念理解云计算 早期的云计算就是虚拟化主机上的分布式计算&#xff0c;现阶段的云计算&#xff0c;已经不单单是一种分布式计算&#xff0c;而是分布式计算、效用计算、负载均衡、并行计算、网络存储、热备份冗杂和虚拟化等计算机技术混合演进并跃升的结果。云计算…

飞书接入ChatGPT,打造属于自己的智能问答助手

文章目录 前言环境列表视频教程1.飞书设置2.克隆feishu-chatgpt项目3.配置config.yaml文件4.运行feishu-chatgpt项目5.安装cpolar内网穿透6.固定公网地址7.机器人权限配置8.创建版本9.创建测试企业10. 机器人测试 转载自远控源码文章&#xff1a;飞书接入ChatGPT - 将ChatGPT集…

太酷了,库昊

昨天晚上凌晨3点30&#xff0c;勇士和国王的第7场比赛开打。 在上一局在勇士主场干翻勇士后&#xff0c;国王队的信心倍增&#xff0c;他们用自己的节奏一次次击溃勇士&#xff0c;特别是今天的前两节&#xff0c;国王能能够回应勇士的进球&#xff0c;防守也更有侵略性。今天不…

Spring第九阶段:Spring的注解功能

注解功能 1、注解配置Dao、Service、Controller组件 通过注解分别创建Dao、Service、Controller Spring配置bean的常用注解有 Controller 配置web层的组件 Service 配置Service组件 Repository 配置Dao组件 Component 配置JavaBean( 除Service , Dao , Controller组件之外的…