name_en: Segment Anything
name_ch: 切分任何东西
paper_addr: http://arxiv.org/abs/2304.02643
doi: 10.48550/arXiv.2304.02643
date_read: 2023-04-07
date_publish: 2023-04-05
tags: [‘深度学习’,‘多模态’]
author: Alexander Kirillov, Meta AI Research, FAIR
citation: 暂无
demo: https://segment-anything.com
论文提出 Segment Anything (SA)模型,无需精调,即可通过文本提示进行图像分割(抠图)。
SA 基于将 Transformer 模型应用到图像处理领域 ViT 备2_论文阅读_ViT,对图像的无监督学习 MAE 备2_论文阅读_MAE,以及文本图像相互映射的CLIP 论文阅读_图像生成文本_CLIP ,可以说它是图像领域大模型落地的一个精典范例。
之前的图像分割模型,比如要识别图中的猫,先需要做一些标注数据,用工具把图中的猫标注出来,然后用这些标注数据在pretrain模型的基础上fine-tune。
SA 论文解决了两个问题:把文字描述和图中形象联系起来;在不fine-tune的情况下解决zero-shot问题。另外,本文的一大亮点是:用先交互后自动的方式标注了数以十亿记的图片,实现了标注功能的自我提升。
Segment Anything (SA)即分割一切,论文的成果是最终发布了模型SAM,它无需fine-tune即可对图中任何物体进行分割,且能通过文本提示分割图像,效果可与有监督学习媲美。论文同时发布了超过1B图片,11M的mask标注的数据集SA-1B。
提示学习帮助大语言模型提升了处理zero-shot问题的能力;CLIP和ALIGN模型又提供了文本和图像对齐的方法,以供下游任务使用,比如DALL-E的生成图片。本文主要研究图像分割:通过文本提示抠图。
具体通过三个相互关联的组件来构建模型:任务、模型、数据。
提示工程近年在自然语言和视觉建模方面产生巨大影响,文中提出了可提示的图像分割。如图1-(a)所示,通过提供图片,及各种各样的提示来分割出所需区域。提示可包含:描述文本、空间中的点(星)、区域(方块)等。在提示不明确的情况下,可能存在多个对象(如:衣服和穿衣服的人),至少能合理地分割其中一个对象。
在预训练阶段,构造了可能与具体使用方法相似的任务以训练模型,生成了具有泛化能力的图像分割器,以解决zero-shot问题。后期可通过提示和下游任务组合,桷建更大系统中的组件来执行新的、不同的任务。
设计模型结构SAM,需要支持:灵活的提示,实时计算,歧意识别。
具体实现如图-1(b)所示,一个图像编码器生成图像嵌入,一个指令编码器生成提示嵌入,然后用一个轻量的mask解码器将二者结合用于分割任务。
基于ViT的图像编码器,只在图像输入时生成一次图像嵌入,嵌入生成后,可与多个提示结合,以节约算力,每次只需要 50ms,以满足web交互的需要。针对歧义问题,设计了一个提示多个mask的方案。
考虑两组提示:稀疏(点、框、文本)和密集(mask)。稀疏提示通过位置编码关联每个提示类型的学习嵌入和来自 CLIP(文本与图像映射)的嵌入。密集提示(mask)使用卷积嵌入,可与图像嵌入逐元素求和。
mask解码器将图像嵌入、提示嵌入和输出token映射到mask。该模型对 Transformer 解码器块进行了修改,后跟动态mask预测头。使用提示自注意力和交叉注意力来更新所有嵌入;然后对图像嵌入进行上采样;MLP 将输出token映射到动态线性分类器,再计算每个图像位置的蒙版是前景的概率。
如果给出的提示不明确,模型将生成多个有效mask。因此,修改模型以预测单个提示的多个输出mask,发现 3 个mask输出足以支持大多数常见情况(嵌套mask通常最多三个深度:整体、部分和子部分)。
大模型需要大量不同分布的图片及mask训练,而现有的数据集并不丰富。
文中提出建立一个数据引擎 data engine,模型标注数据,数据又反过来训练模型,循环往复。具体包含三个阶段:
最终产生SA-1B数据集,超过 10 亿个带mask的数据集,图片全部由SAM自动标注,平均每个图像100个mask。
建立自己去meta网站试一试,不用梯子即可使用。
https://segment-anything.com/demo
自己上传图片试了一下,把头发和脸分开,两只手可以分开,肉色的衣服和皮肤,边缘还比较完美,mask后效果就很像动画效果。不知道修图师和插画师作何感想,娃们还会不会再去学插画和素描?是不是应该先去研究一下AlphaGo出来之后,围棋班有没有受影响?
源码基于Pytorch,从predictor_example来看,接口非常简单,只要稍微做过一些图像模型的人都能看懂,mask区域被直接返回,我没找到调用CLIP的图文对齐部分,只试用了切割部分。
下载源码
git clone https://github.com/facebookresearch/segment-anything.git
按README.txt中提示安装即可
基于docker运行
docker pull pytorch/pytorch:1.13.1-cuda11.6-cudnn8-runtime
进入docker后,安装jupyter
pip install jupyter_nbextensions_configurator jupyter_contrib_nbextensions
jupyter notebook --allow-root -y --no-browser --ip=0.0.0.0
我的环境还安装了以下工具
apt-get update
apt-get install build-essential libgl1-mesa-glx libglib2.0-0
pip install matplotlib torchvision pycocotools onnx black isort opencv-python
测试一下不同参数量的模型:
ViT-B(base), ViT-L(Large), ViT-H(Huge)。
默认使用ViT-H,下载约2.4G,GPU内存用满11G。
wget https://dl.fbaipublicfiles.com/segment_anything/sam_vit_h_4b8939.pth
效果如下:
下载ViT-B,下载约358M,GPU内存用到8G左右,
wget https://dl.fbaipublicfiles.com/segment_anything/sam_vit_b_01ec64.pth
比较后可以看到,大模型的mask效果明显更好一些:
不是特别大的模型,如果有GPU,在家用速度也能接受,从此拥有了自己的抠图小助手。