在浏览器里去掉照片背景:模型是什么、显卡为什么要紧、哪些照片它做不好

一个 44 MB 的神经网络在你自己的机器上把主体抠出来。笔记本显卡上不到一秒,CPU 上 15–25 秒。ISNet 是什么、为什么不用上传,以及它会做错的那几类照片。

一句话

去背景以前意味着把照片传到一台有显卡的服务器上。现在不必了。一个小到可以一次性下载(44 MB)的分割模型可以在浏览器里跑:机器支持 WebGPU 时,一张照片远不到一秒;不支持时,同一个模型在 CPU 上跑 15–25 秒。两种情况下照片都不离开设备。这个模型对背景分明的人物、商品、动物效果好,对发丝叠在发丝上、玻璃,以及任何连摄影师都看不清边缘的东西效果差。

模型是什么

工具用的是 ISNet,来自论文 Highly Accurate Dichotomous Image Segmentation(Qin 等,ECCV 2022)。“Dichotomous”(二分)的意思是任务是二元的:每个像素,是前景还是不是。ISNet 在 DIS5K 数据集上训练——五千张高分辨率图片,配有极其精细的像素级蒙版,对象是自行车、椅子、树这类东西,选它们正因为细枝细杈会打败早先的模型。对 1024 × 1024 的输入,它输出一张 1024 × 1024 的概率图;工具对这张图取阈值、羽化边缘,作为 PNG 的 alpha 通道。

权重以 Apache-2.0 发布。本站自己托管,切成三段以便断点续传,第一次用过之后缓存在浏览器里:第二张照片不再下载任何东西。

“在浏览器里”为什么现在做得到

两样东西得先存在。ONNX Runtime Web 在 JavaScript 里执行训练好的模型,算术运算要么由 WebAssembly 在 CPU 上做,要么——从 2023 年起——由 WebGPU 做,那是把显卡开放给通用计算的浏览器 API。一次分割前向传播是几千亿次乘加,显卡就是为这个造的,单个 CPU 线程不是。

本站工具自己的数字,同样是 1024 像素输入:

路径 在哪跑 每张耗时
WebGPU Chrome / Edge 113+、Safari 26+,带任何现代显卡的笔记本或台式机 不到 1 秒
WebAssembly 任何浏览器,单线程 15–25 秒

WebAssembly 路径是故意单线程的。多线程 WASM 要求页面处于跨源隔离状态,那个响应头会挡掉所有第三方脚本——包括养活这个站的广告代码。单线程慢,但页面得以免费;活儿被挪进 Web Worker,所以它在磨的时候界面不卡。

内存是另一个约束:运行时加模型加中间激活值需要大约 200 MB 空闲内存。4 GB 内存的手机在 CPU 路径上撑得住;一些更老的手机根本分配不出这块缓冲区,工具会直接说明,而不是让标签页崩掉。

它做不好的,实话实说

  • 发丝对着相近的背景。 深色头发对深色墙、金发对米色窗帘。模型看不到边缘,因为像素里根本没有边缘。蒙版要么吃掉头发,要么留一圈墙。
  • 透明和反光的东西。 玻璃、水、主体前面的酒杯。分割是二元的;玻璃既不是前景也不是背景,结果是一条硬边穿过它。
  • 运动模糊。 模糊的边缘没有唯一正确的分界线。
  • 多个主体。 模型保留它认为是“主体”的一切;两个人通常都留,一个人和一条大狗可能只留一个。
  • 很小的主体。 输入长边 1024 px;一张远景里 60 px 高的人,变成蒙版里的几十个像素,出来是一团。

干净的商品图、素墙前的人像、地板上的宠物、纸上的 logo,它很可靠——训练集里装满的就是这些。

拿到结果之后

输出是带真实透明通道的 PNG。这是放进幻灯片、商品页或另一张照片的正确格式,也是发邮件的错误格式——1200 万像素的 PNG 抠图有 20–30 MB。目的地要小文件又不需要透明,就转成白底 JPEG;需要透明又要更小,带 alpha 的 WebP 是 PNG 的三分之一。压缩两种都能处理。

本文用到的工具