Background Matting详解

article/2025/9/28 4:52:37

转自:https://zhuanlan.zhihu.com/p/148265115?from_voters_page=true
https://www.aiuai.cn/aifarm1462.html

使用人工智能技术实现类似PhotoShop等工具的抠图功能是一个非常有趣且有科研前景的一个方向。和分割算法只有  和  两个值相比,抠图得到的边缘更加平滑和自然,且包含透明通道信息。抠图方法可以概括为:  。其中  是输入图像,  表示图像  的的前景,  表示背景,  表示该像素为前景的概率,Matting通常是指由图像内容和用户提供的先验信息来推测  ,  以及  。从技术角度来讲,抠图有传统方法和深度学习方法两种;从交互方式来看,抠图包括有交互和无交互两种,有交互的抠图通常需要用户手动提供一个草图(Scratch)或者一个三元图(Trimap)。这篇文章要介绍的是一篇基于深度学习的无交互的抠图方法,在目前所有的无交互的抠图算法中,Background matting是效果最好的一个。它的特点是要求用户手动提供一张无前景的纯背景图,如图1所示,这个方法往往比绘制三元图更为简单,尤其是在视频抠图方向 。这个要求虽然不适用于所有场景,但在很多场景中纯背景图还是很容易获得的。

图1:Background matting的使用流程

图1:Background matting的使用流程

在训练模型时,用户首先使用Adobe开源的包含alpha通道数据的数据集进行数据合成,然后在合成数据上进行有监督的训练。为了提升模型在真实场景中的泛化能力,由于这种数据往往都是无标签的。所以Background Matting使用一个判断图像质量的判别器来对无标签的真实场景的数据进行训练。源码已开源Background-Matting。


1. 算法详解

图2:Background Matting的生成模型

如图2所示,Background Matting的创新点有三个:

  • 输入使用了背景图,分割结果,连续帧(视频)作为先验信息;
  • 提出了Context Switching Block模块用于整合上面的数据;
  • 提出了半监督的学习方式来提升模型的泛化能力。

下面将对以下三点详细展开。

1.1 网络结构

1.1.1 输入

从图1中我们可以看出,Background Matting共有四个输入,其中 Input(  )和Background(  )比较好理解,就是使用同一台拍摄设备在同一个环境下拍摄的有人和无人的两张照片。在尝试该算法的过程中,发现一个重要的一点是当拍摄照片时,要保证Input的背景和无人的Background的内容保持一致,要尽量避免阴影和反射现象的出现。Soft Segmentation(  )是由分割算法得到的掩码图,论文中的分割算法使用的是Deep Labv3+,它使用类似于其它生成三元图的类似的方法来进行处理,包括10次腐蚀,5次膨胀以及一次高斯模糊。这一部分在test_background-matting_image.py的141-143行。

rcnn = cv2.erode(rcnn, kernel_er, iterations=10)
rcnn = cv2.dilate(rcnn, kernel_dil, iterations=5)
rcnn=cv2.GaussianBlur(rcnn.astype(np.float32),(31,31),0)

Motion Cuses(  )是在处理视频时当前帧的前后各20和40帧,即  ,这些帧转化为灰度图后合成一个batch形成  。

1.1.2 生成模型

Background Matting可以看做一个‘编码器-解码器’的结构,其中编码器又叫做Context Switching Block,它是由EncoderSelector以及Combinator组成,下面结合源码对齐细节进行介绍。

Encoder:在Encoder中,四个输入图像将会被编码成不同的Feature Map,网络结构的细节可以去network.py文件去查看。其中输入图像的网络结构在18-20行:

model_enc1 = [nn.ReflectionPad2d(3),nn.Conv2d(input_nc[0], ngf, kernel_size=7, padding=0,bias=use_bias), norm_layer(ngf), nn.ReLU(True)]
model_enc1 += [nn.Conv2d(ngf , ngf * 2, kernel_size=3,stride=2, padding=1, bias=use_bias),norm_layer(ngf * 2),nn.ReLU(True)]
model_enc2 = [nn.Conv2d(ngf*2 , ngf * 4, kernel_size=3,stride=2, padding=1, bias=use_bias),norm_layer(ngf * 4),nn.ReLU(True)]

它是由一个镜面padding(用于提升模型在边界处的抠图效果),连续3组步长为2的卷积,BN,ReLU组成,最终得到的Feature Map的尺寸是  ​,这个Feature Map即是源码中的img_feat。另外三个图像  ,  ,  和输入图像的编码器的结构相同,具体代码见23-44行,它们编码之后的Feature Map依次是back_featseg_feat以及multi_feat

Selector:图1中另外一个重要的结构是Selector,它依次把back_featseg_feat以及multi_feat分别和img_feat拼接成一个Feature Map,然后经过三个结构相同的Selector得到三组和输入图像合并之后的Feature Map,它们依次是comb_back,Comb_seg以及comb_multi。Selector结构在源码的54-56行。

self.comb_back=nn.Sequential(nn.Conv2d(ngf * mult*2,nf_part, kernel_size=1, stride=1, padding=0, bias=False), norm_layer(ngf), nn.ReLU(True))
self.comb_seg=nn.Sequential(nn.Conv2d(ngf * mult*2, nf_part, kernel_size=1, stride=1, padding=0, bias=False), norm_layer(ngf), nn.ReLU(True))
self.comb_multi=nn.Sequential(nn.Conv2d(ngf * mult*2, nf_part, kernel_size=1, stride=1, padding=0, bias=False), norm_layer(ngf), nn.ReLU(True))

Combinator:Combinator将三组Selector得到的结果comb_back,Comb_seg以及comb_multi和输入图像的编码结果img_feat拼接成一个Feature Map,拼接见源码的99和101行,网络结构为1组1×11\times11×1卷积+BN+ReLU的组合,得到的结果是model_res_dec,见源码的59行。

model_res_dec=[nn.Conv2d(ngf * mult +3*nf_part, ngf*mult, kernel_size=1, stride=1, padding=0, bias=False), norm_layer(ngf*mult), nn.ReLU(True)]
...
oth_feat=torch.cat([self.comb_back(torch.cat([img_feat,back_feat],dim=1)),self.comb_seg(torch.cat([img_feat,seg_feat],dim=1)),self.comb_multi(torch.cat([img_feat,back_feat],dim=1))],dim=1)
out_dec=self.model_res_dec(torch.cat([img_feat,oth_feat],dim=1))

至此,Context Switching Block部分介绍完毕。

共享残差:紧跟着Context Switching Block的是一组7个残差模块组成的解码网络(60-61行)。残差模块定义在ResnetBlock类中,包括卷积,Dropout等操作,详见源码的204-244行。经过共享的解码结构之后,网络会分成两个分支的多头输出,它们分别用于前景FFF和概率通道α\alphaα的输出,我们下面对这两个分支分别进行介绍。

前景预测分支:在这个分支中,它首先将共享残差的解码经过一组3个残差块的解码器进行继续解码,得到名为out_dec_fg的Feature Map。解码的第一部分使用out_dec_fg作为输入,经过一组双线性差值上采样,卷积,BN,ReLU操作后得到out_dec_fg1。解码的第二部分使用out_dec_fg1img_feat拼接之后的结果,依次经过双线性差值上采样,卷积,BN,ReLU,镜面Padding,卷积后得到model_dec_fg2。这一部分的核心代码如下:

model_res_dec_fg=[]
for i in range(n_blocks2):model_res_dec_fg += [ResnetBlock(ngf * mult, padding_type=padding_type, norm_layer=norm_layer, use_dropout=use_dropout, use_bias=use_bias)]
...
model_dec_fg1=[nn.Upsample(scale_factor=2,mode='bilinear',align_corners = True),nn.Conv2d(ngf * 4, int(ngf * 2), 3, stride=1,padding=1),norm_layer(int(ngf * 2)),nn.ReLU(True)]
model_dec_fg2=[nn.Upsample(scale_factor=2,mode='bilinear',align_corners = True),nn.Conv2d(ngf * 4, ngf, 3, stride=1,padding=1),norm_layer(ngf),nn.ReLU(True),nn.ReflectionPad2d(3),nn.Conv2d(ngf, output_nc-1, kernel_size=7, padding=0)]
...
self.model_res_dec_fg=nn.Sequential(*model_res_dec_fg)
self.model_dec_fg1=nn.Sequential(*model_dec_fg1)
self.model_fg_out = nn.Sequential(*model_dec_fg2)
...
def forward(self, image,back,seg,multi):out_dec_fg=self.model_res_dec_fg(out_dec)out_dec_fg1=self.model_dec_fg1(out_dec_fg)fg_out=self.model_fg_out(torch.cat([out_dec_fg1,img_feat1],dim=1))

 预测分支:和前景预测分支类似,它首先经过一组3个残差块的解码器进行继续解码,然后经过两组双线性差值,卷积,BN,ReLU操作进行解码,最后经过一组镜面Padding,卷积以及Tanh之后得到最终预测的alpha matte,使用Tanh的原因是因为alpha matte的每个像素的值需要介于0和1之间。这一部分的核心代码如下:

model_res_dec_al=[]
for i in range(n_blocks2):model_res_dec_al += [ResnetBlock(ngf * mult, padding_type=padding_type, norm_layer=norm_layer, use_dropout=use_dropout, use_bias=use_bias)]
model_dec_al=[]
for i in range(n_downsampling):mult = 2**(n_downsampling - i)model_dec_al += [nn.Upsample(scale_factor=2,mode='bilinear',align_corners = True),nn.Conv2d(ngf * mult, int(ngf * mult / 2), 3, stride=1,padding=1),norm_layer(int(ngf * mult / 2)),nn.ReLU(True)]model_dec_al += [nn.ReflectionPad2d(3),nn.Conv2d(ngf, 1, kernel_size=7, padding=0),nn.Tanh()]
...
self.model_res_dec_al=nn.Sequential(*model_res_dec_al)
self.model_al_out=nn.Sequential(*model_dec_al)
...
def forward(self, image,back,seg,multi):out_dec_al=self.model_res_dec_al(out_dec)al_out=self.model_al_out(out_dec_al)

1.1.3 判别模型

为了提升在真实场景的抠图效果,Background Matting使用了基于pix2pix hd中提出的多尺度判别器(注:论文中给出的是使用PatchGAN,源码的实现是基于多尺度判别器,两个算法大同小异,不影响Background Matting的整体框架,这里以源码为准)的对抗训练对真实场景的无标签数据进行训练。

图3:使用无监督的GAN进行微调,这里将前景结果贴到一个新的背景之上,让判别器区域是真样本还是假样本

 

在这里我们先对判别器模型结构进行介绍,训练方式见loss部分。判别器的网络结构位于network.py文件中的249行-340行。判别器的主类是MultiscaleDiscriminator,在多尺度判别器的每个尺度又使用了3个线性判别器。每个线性判别器都一个全卷积网络,由若干组卷积,BN和Leaky ReLU组成。判别器的3个尺度分别为:原图,原图的1/2,原图的1/4。不同尺度的判别器的优点在于越粗糙的尺度感受野越大,越容易判别全局一致性,而越精细的尺度感受野越小,越容易判别材质,纹理等细节信息。

1.2 模型训练

Background Matting使用了基于Adobe Matting Dataset的合成数据和无标签的真实数据的半监督方式进行模型训练,所以模型训练也氛围有监督学习部分和无监督学习部分。

1.2.1 有监督学习

正如在1.1.1中介绍的,网络的输入 由输入图像,无人像背景 ,软分割效果以及运动信息  构成,即  。在无视频的场景下,  由  的灰度图组成。因此这个模型可以表示为:

 

其中  是有监督学习需要学习的参数,  就是1.1.2中介绍的生成模型。

Adobe Matting数据集有450个前景图  以及对应的alpha掩码  组成,这里选取了和人类比较类似的280个样本用于数据合成。背景则是取自于coco数据集。为了避免模型过于偏向于学习  和  的差值,这里对  进行了一些变换得到  ,例如gamma矫正,高斯模糊等。  是由DeepLab v3的输出经过10-20次的腐蚀以及15-30次的膨胀以及高斯模糊得到的。有监督学习的loss可以表示为:

 

1.2.2 对抗训练

基于1.2.1训练的数据都是基于合成的,但是只基于这些数据并无法得到非常好的人像抠图模型。难点有4个:

  • 人像的细节非常难以处理;
  • 分割效果如果不好的话对抠图的准确率影响很大;
  • 前景和背景颜色接近时抠图很难;
  • 有人像和无人像的背景图的对齐。

如果把失败的抠图效果合成到背景图中,这种生成的图像明显和真实拍摄的图像有很大的差距。基于这个思想,作者提出了使用对抗网络来进行网络参数的微调。也就是说,使用判别器来判断一个图片是合成的图像还是真实拍摄的图像,如果合成的图像足以骗过判别器,这就足以表明判别器优化到了一个比较好的参数值。也就是说,生成器生成的数据应最小化判别器判别的结果,这也就是对抗训练损失的第一个部分。

 

如果只是端对端的对判别器和生成器进行训练,网络会容易陷入到处处  的局部最优值。也就是说,生成网络只需要生成和输入图像完全一致的matting图,这时候判别器是无法判断一个图像是生成器生成的还是原始图像。

因此,Background Matting使用了在Adobe matting数据集上得到的模型作为指引来进行Teacher-Student学习,如图3所示。具体的讲,对于一个输入图像III以及与其对应的输入XXX,我们首先使用基于Adobe数据集训练的模型得到“伪Ground Truth”:  。然后我们使用真实数据训练一个基于真实数据的matting模型  。对抗训练的损失函数便是最小化Adobe数据集和真实数据集的差距。损失函数的最后便是根据预测的alpha和前景区域合成新的图像,然后最小化这个图像与输入图像的差值。

综上,对抗训练的损失函数可以表示为最小化  ​和  之和:

 

1.3 测试

测试过程分成以下几步:

  1. 根据输入数据  ,准备对应的背景  ,软分割  ,以及运动序列  。如果要处理的是图片,则用输入图像的复制代替;
  2. 根据场景或者效果选择对应的抠图模型,作者提供了syn-comp-adobereal-fixed-cam以及real-hand-held三个模型。
  3. 根据模型的输出生成对应的效果图。



2. 总结

根据作者在附录中提供的内容,算法核心的每一个部分都起着非常重要的作用,似乎少了其中任何一个模块抠图效果都会大打折扣。算法的Context Switching Block的设计非常巧妙,利用GAN来进行半监督的学习提升在真实场景的数据也非常有意思,整个模型的算法非常精彩。

为了更好的使用该模型,作者在自己的博客中给出了若干条建议,首先是不要在生成的背景图和前景图区别过于大的环境下使用,包括动态的背景,会产生影子的区域,影响曝光的场景。这一部分的根本原因在于输入的B′B'B′和要预测的BBB差距过大,这一些变化的区域会被误识为前景区域。然后在进行拍摄时,作者建议关闭自动曝光和自动对焦,且使用摄影模式来拍摄有无人像区域,无背景的区域靠人离开拍摄区域来取得。所有这些的目的都是为了保持背景图片的一致性。

经过笔者尝试,虽然这个方法要求提供的数据最多,但它的最大优点是一个无交互的模型,而多的拍摄背景图的步骤远比手动绘制草图或者三元图的方式容易的多。在抠图效果上,它可以说是所有无交互模型中效果最好的,就算和绝大多数有交互的模型相比,它的效果也能排在前列。

Background Matting的另外一个好处是它提供了无监督的训练方式,使得用户可以根据自己的数据场景来训练自己的模型。这使用它有了更广泛的应用前景。

 


http://chatgpt.dhexx.cn/article/A04W9oha.shtml

相关文章

【Matting】MODNet:实时人像抠图模型-onnx python部署

上一篇博客【Matting】MODNet:实时人像抠图模型-笔记分析了MODNet的原理,本篇博客将使用python部署MODNet官方提供的onnx模型,其效果如下: 在线人像抠图体验:CV案例 相关部署链接: 【Matting】MODNet&…

【笔记】Robust High-Resolution Video Matting with Temporal Guidance

Robust High-Resolution Video Matting with Temporal Guidance算法笔记 一、算法简介二、网络结构三、训练1、数据集2、训练过程3、损失函数 Robust High-Resolution Video Matting with Temporal Guidance 论文地址 RobustVideoMatting 代码地址 Robust High-Resolution Vide…

【Matting】MODNet:实时人像抠图模型-笔记

paper:MODNet: Real-Time Trimap-Free Portrait Matting via Objective Decomposition (AAAI 2022) github:https://github.com/ZHKKKe/MODNet 抠图在线体验:CV案例 部署教程: 【Matting】MODNet:实时人像抠图模型…

Image Matting 客观评价指标、数据集及主观评价

Image Matting 客观评价指标、数据集及主观评价 2021.7更新 PPM-100数据集已经开放,GitHub,详情见下文章节2.4 目录 Image Matting 客观评价指标、数据集及主观评价2021.7更新 客观评价指标1. 精度1.1 SAD1.2 MSE 均方误差1.3 Gradient error1.4 Conne…

深度学习(7)之图像抠图 Image Matting算法调研

目录 1.Trimap和Strokes 2. 相关数据集 3.论文算法调研 3.1 Deep Image Matting 3.2 Semantic Image Matting 3.3 Background Matting 3.4 Background Matting V2 3.5 Semantic Human Matting 3.6 HAttMatting 3.7 MMNet:Towards Real-Time Automatic Portrait Matt…

【SHM】Semantic Human Matting抠图算法调试

前言: 2018年阿里的论文《Semantatic Human Matting》给出了抠图领域的一个新方法,可惜阿里并没有公布源码,而牛人在Github上对这个论文进行了复现,我也是依赖Github上的工程进行钻研,而在调试的过程中,发…

[Matting]论文阅读:Deep Image Matting 详细解读

[Matting]论文阅读:Deep Image Matting 详细解读 一 、摘要 任务二、方法2.1 第一部分(Matting encoder-decoder stage)2.2 第二部分(Matting refinement stage)2.3 数据部分(Composed Datasets&#xff09…

【CVPR2022】MatteFormer: Transformer-Based Image Matting via Prior-Tokens

MatteFormer: Transformer-Based Image Matting via Prior-Tokens 中文题目: 借助先验Token的基于Transformer的图像抠图 paper:https://arxiv.org/pdf/2203.15662v1.pdf code:https://github.com/webtoon/matteformer 摘要 本文提出了一个基于Tran…

Image Matting代码和算法效果总结

本文参考了:http://blog.leanote.com/post/610167078qq.com/Image-Matting。作者给出了大部分matting-code的链接,说明也比较细致、系统,在这里向作者表示由衷地感谢!以下是博客的原文: 肖总博客:http://3…

matting笔记_一周小结

去年刚入坑的旧笔记,刚翻出来… 1. 利用神经网络做抠图的入坑之作《Deep Image Matting》 详情见之前的笔记 matting系列论文笔记(一):Deep Image Matting 由于image matting的工作没有特别好的综述,有的综述也不是…

Matting 基于DeepLearning 入门

前言 是比较清晰的用思维导图的形式介绍了一些Matting 基于DeepLearning 的经典论文,如 Deep Image matting可以通过这篇初步了解深度学习Matting领域该篇论文可以看作是基于深度学习研究Matting的开山之作,之后的许多有效、可行度高的做法都是基于这篇…

Matting和Segmentation区别及模型概述

一、两者区别 Segmentation:常被认为是硬分割(Hard Segmentation),就是将图片中的像素分成多个类别,如果是前背景分割,那么就是分成两个类别,一个类别代表前景,一个类别代表背景。而…

如何清除Safari,Chrome和Firefox中的缓存,历史记录和Cookie

如何清除浏览器的cookie缓存?许多网站的通知,用户记住账号密码登录状态,都是通过浏览器cookie缓存,定期清理Safari,Chrome和Firefox中的缓存,历史记录和Cookie,可以让浏览器保持一个良好的状态,也可以保护我们的隐私。…

Nginx缓存服务

文章目录 一、缓存概述(1)缓存的作用(2)缓存常见的类型(3)Nginx缓存的原理 二、配置Nginx缓存(1)主配置文件中缓存的语法(2)配置Nginx缓存-实验环境-实验目的…

android7.0清除缓存,iPhone7如何清理应用缓存 iphone7清理应用缓存教程

手机使用后会留下一些缓存垃圾,那么 iPhone7如何清理应用缓存? 下面就带来iphone7清理应用缓存教程,一起来学习下。 方法1:强行重启 强行重启(也叫冷重启)能够帮助iOS的设备清理一下临时文件,定期强行重启一下设备&…

Chrome Edge Firefox Safari 如何清除 DNS 缓存

Chrome Edge Firefox Safari 如何清除 DNS 缓存 如何清除浏览器的 DNS 缓存 (Chrome, Firefox, Safari) Chrome Chromium Edge Firefox Safari clear DNS Cache, flush DNS cache 请访问原文链接:https://sysin.org/blog/clear-browser-dns-cache/,查…

苹果电脑怎么清理垃圾和缓存文件,mac如何清理系统缓存文件

电脑使用的时间越久,系统运行就会变得越来越卡,这是Windows和Mac系统都会出现的现象。为了提高系统运行速度,我们有必要清理一下电脑缓存。那么苹果电脑怎么清理垃圾和缓存文件?本指南将详细讲解清理Mac缓存的技巧,还补…

浏览器缓存导致的问题:

1、需要的效果如下: 2、添加样式之后,样式会生效,但是没有达到上面的效果,表单会消失掉,只剩下一个黑色的背景图 4、原因: 因为浏览器的缓存问题导致的样式没有显示出来 5、解决办法: 清除掉…

浏览器缓存

文章目录 前端缓存|后端缓存按缓存位置分类缓存过程memory cachedisk cacheService WorkerPush Cache 强制缓存适用场景ExpiresCache-Control 协商缓存(也叫对比缓存)适用场景ETag和Last-Modified区别 缓存相关问题缓存穿透缓存击穿缓存雪崩 前端缓存|后…

苹果清除缓存_苹果手机卡顿别着急换,调整这5个功能,iPhone 6S还可以再战两年...

阅读本文前,请您先点击上面的“议科技”,关注,这样您就可以继续收到最新文章了。每天都有分享。完全是免费订阅,请放心关注。 平时在使用苹果手机的时候,时间用久了,是不是觉得手机有些卡顿?使用…