自动标注三件套实战:Grounded-SAM + autodistill + X-AnyLabeling 构建高效数据流水线
发布时间:2026/10/2 19:02:04来源:尧图网络
做数据标注这行最烦的就是重复劳动。一个框一个框去点、去拖、去调整顶点几千张图下来眼睛都快瞎了。手速再快也顶不住数据量增长而且不同人标注的尺度还不一样同一个人上午和下午的标准都能飘。我这一年多一直在折腾自动标注这条路从半自动到全自动从单模型到多模型配合最后稳定用下来的组合就是 X-AnyLabeling 加 autodistill 加 Grounded-SAM 这三件套。这篇就把整套流程拆开讲透从原理到实操包括我踩过的坑一次性都交代了。先说清楚这套东西能解决什么问题。简单讲就是用 Grounded-SAM 这种大模型当“老师”把没标注的图片自动识别出目标并生成精细的掩码用 autodistill 把这套“老师”逻辑封装成流水线批量处理、格式转换一把梭最后用 X-AnyLabeling 当“人工质检台”把自动标注的结果拉进来人工审核修正。三个工具各管一段组合起来就是一条从原始图片到可用训练集的完整流水线。不管是做目标检测、实例分割还是语义分割的数据集这套流程都能用尤其适合那种数据量几千上万、类别固定、标注规范明确的场景。1. 整体设计思路为什么是这三件套1.1 手动标注的痛点与自动化的核心逻辑先聊聊数据标注这个环节在整个项目里的位置。CV 项目的模型训练、调参、部署每一样都有成熟的工具链和教程唯独数据标注这件事听起来简单做起来磨人。我最早用 LabelImg后来换 labelme体验就是效率天花板太明显了。一张图如果有五六个目标光拖框和抠多边形就要一两分钟遇到边缘复杂的物体更是折磨船翻了都要重新来。整个项目几百G的数据光标注就占掉三四周训练本身反而只要一两天。当时我就在想有没有一种方式能把这种重复劳动压缩掉 80% 以上。后来慢慢摸索出来一条思路先把自动标注模型跑出结果人工只做审核和修正。这个逻辑听起来简单但真正落地要解决三个问题自动标注的模型从哪来、怎么批量跑、结果怎么交给人工快速修正。这三个问题刚好对应 Grounded-SAM、autodistill、X-AnyLabeling 三个工具。这个思路本质上是一种“人机协作”的工作流。大模型负责“尽力而为”地生成标注雏形人的精力从“逐像素绘制”转变为“审核和微调”效率提升非常明显。我们实测同一个项目纯手工一个人一天最多 200-300 张人机协作可以干到 1500-2000 张而且修正工作比从零开始画要省力得多因为框的位置和掩码的轮廓已经八九不离十了。1.2 三个工具在流水线中的定位分工Grounded-SAM是整个流程里的“智能标注员”。它把两个模型串联在一起用 Grounding DINO 做开放集检测再让 SAM 为检测结果生成像素级分割掩码。也就是说你告诉它“请找到图像中的水杯、鼠标、显示器”它就能把每个目标的位置框出来并且把目标轮廓的精细掩码也一并生成。autodistill是“流水线管理员”。它本身就是一个自动化标注框架把 Grounded-SAM或者其他基础模型封装成标准化的接口同时提供数据集的存储、格式转换、模型训练的完整流程。简单说autodistill 让“调用 Grounded-SAM 批量标注 1000 张图片”这件事变成了一段代码能搞定的事而不是要自己写一堆 IO 和逻辑。X-AnyLabeling是“人工质检员”的操作台。它是一个带 GUI 的开源标注工具特别关键的一点是它支持导入多种格式的标注文件并且直接内嵌了 AI 自动标注能力。我们用它来打开 autodistill 生成的标注结果人工在界面上检查、修正、确认最后导出成目标格式。这个工具让“人工审核”这个环节变得非常高效因为它不是让你重新标注而是让你在已有结果上做微调。这三个工具的分工可以类比成一条生产线Grounded-SAM 是产线上的机械臂干活autodistill 是调度系统排产X-AnyLabeling 是质检台的屏幕和工具人工把关。任何一个环节缺失流程都会变得割裂。只上自动标注出来的结果有人工复核会很乱误标漏标只上人工标注效率又回到底线的状态只靠脚本硬凑格式转换和异常处理就是新的大坑。1.3 适用场景与边界判断这套流程不是万能药我自己试下来比较适合的场景有三个特征第一图像中的目标物是常见类别比如人、车、动物、日常用品这类。因为 Grounded-SAM 的效果跟文本检测基座的能力正相关如果是极度小众的物体比如某种特殊的工业零件、罕见昆虫亚种效果就会明显下滑需要人工修正的量陡增反而得不偿失。第二标注规范明确且相对统一。比如“人都要标注”“车辆要标注到车身钣金边缘”这种规则模型不需要理解规则但人工修正时有明确的判断依据流程更顺畅。第三数据量中等偏大几千张以上且时间紧张。几百张的量手动标注也就一两天的活搭建整套环境反而费时费力。自动标注的真正价值在于规模效应量越大省的时间越明显。我后来还把这套流程用在一个“掌心常见小物件”数据集上大约 4000 张图片目标类别 12 种。第一轮自动标注的初始置信度高、掩码质量也好的大约有 7 成左右剩下 3 成需要人工修正。即便这样整个项目的标注周期也从预估的 9 天压到了 2 天半。对于这种“量大、类别常规”的典型场景这套自动标注流程的投入产出比很高。2. 环境准备与工具选型2.1 硬件与基础环境配置先说硬件底线Deep Learning 那个方向避不开的是显存。Grounded-SAM 这条链路的显存占用大头主要在 SAM 模型我们用默认配置跑 1080p 图片的时候显存峰值大概在 6-8GB 之间。如果图片分辨率再高或者一次处理批次过大可能会冲到 10GB 以上。所以一张 8GB 显存的显卡是起步线16GB 会更从容。CPU 和内存的影响相对小但标注大量数据时 CPU 会被图像解码和预处理的活儿顶起来建议内存至少 16GB。系统方面我在 Ubuntu 20.04 和 Windows 11 上都跑过。Ubuntu 上环境部署更顺滑依赖冲突少推荐作为主力。Windows 上其实也能跑只是有些 Python 包需要额外处理 MSVC 编译环境比较费神。如果你只是用 X-AnyLabeling 的人工审核功能它是完全跨平台的Windows 上用起来反而最顺手。Python 版本建议锁定 3.10别用 3.11 或更高某些依赖比如特定版本的 PyTorch、Grounding DINO 相关的编译包在 3.10 上最稳。我用 conda 建独立环境避免和别的小项目互相污染。2.2 X-AnyLabeling 安装要点X-AnyLabeling 安装方式挺亲民的GitHub 上直接拉源码就行。git clone https://github.com/vietanhdev/anylabeling.git cd anylabeling pip install -r requirements.txt python anylabeling/app.py拉源码后第一次启动会在后台下载几个默认模型权重网络状态不好的话这一步容易卡住甚至直接闪退。解决办法是手动把模型文件下载好放到它指定的~/.anylabeling目录下面具体模型文件可以看它 GitHub README 里的链接。如果你在国内网络环境可能要手动处理一下下载代理的问题或者找一个网速稳定的时段来拉权重。这个工具本身界面逻辑很简单左上角选模型画布上拖拽标注快捷键 W 画框、E 画多边形、Q 选择/移动中键拖动平移滚轮缩放。人工审核自动标注结果主要就是这几个键熟练之后操作速度非常快。有一点特别提一下X-AnyLabeling 默认模型列表里就有 SAM 系列包括 SAM ViT-B、MobileSAM 等这意味着你甚至可以在 GUI 里直接对单张图做自动标注不需要走 autodistill 那套批量逻辑。我把 X-AnyLabeling 的“AI 辅助”定位成“单图打补丁”模式特别适合那种批量标注完之后的抽查与修正环节。2.3 autodistill 安装要点autodistill 是 Roboflow 出的开源框架安装非常简单pip install autodistill autodistill-grounded-sam注意要配合一个 Grounded-SAM 的封装包。核心 API 就三行from autodistill_grounded_sam import GroundedSAM from autodistill.detection import DetectionOntology from autodistill.utils import plot base_model GroundedSAM( ontologyDetectionOntology.from_string(person. car. dog.), box_threshold0.35, text_threshold0.25 )这里的ontology就是类别清单模型会根据这里写的文本去识别目标。注意一个细节如果你不设置OPENAI_API_KEY这个库会直接用你输入的文本去跑 Grounding DINO如果设置了它还会用 Llama/OpenAI 对 prompt 做一轮扩展生成更丰富的描述词来提升召回率。我实际测试下来设置 API key 之后对低置信度区域的召回确实有提升但如果你不方便配置外部 API 调用不设置也能跑只是要接受模型按字面词检索的局限性。2.4 Grounded-SAM 模型部署细节Grounded-SAM 本身不是一个 pip 包而是一个 GitHub 项目需要拉代码和权重文件git clone https://github.com/IDEA-Research/Grounded-SAM.git cd Grounded-SAM pip install -r requirements.txt权重文件有两个Grounding DINO 的一般用groundingdino_swint_ogc.pth大约 700MB和 SAM 的ViT-B 大约 375MBViT-H 大约 2.5GB。默认代码会假设权重文件放在指定路径我建议把两个权重统一放到./weights/目录下然后在代码里显式拼接路径。实际跑推理时可以先跑一个小数据集做验证确认检测结果符合预期之后再全量跑。显存优化方面SAM 的model_type有vit_b、vit_l、vit_h三档。我的经验是初始自动标注用 vit_h 效果最好但如果你显存只有 8G强烈建议用 vit_b 或 vit_l。vit_h 的掩码边缘精度确实高但 1080p 图片单张推理时间大约是 vit_b 的 3-4 倍在大批量场景下这个时间成本非常高。如果你对掩码边缘质量不是极致要求或者后续还要人工修正vit_b 完全够用。初期选型如果拿不准用 vit_b 试跑一批看看效果再决定。3. 核心细节解析每个环节的关键决策与逻辑3.1 Grounded-SAM 的文本检测链路与提示词设计Grounded-SAM 的原理值得展开讲一下因为它直接决定了我们后面怎么调参数。它由两段模型串联Grounding DINO一个开放集目标检测模型输入文本输出目标框。它把文本编码器输出的特征与图像特征做跨模态匹配所以它能检测“训练时没见过”的类别只要文本提示词描述得足够准确。SAM拿到 Grounding DINO 输出的目标框作为“提示”在框内分割出像素级掩码。SAM 的训练目标就是“给定任何分割提示输出高质量掩码”所以它对边缘细节的处理能力很强。两段模型默认独立运行所以提示词的设计非常关键。我举一个实际例子我在一个“工地安全装备检测”项目里直接写 “helmet” 时漏检率很高因为模型把安全帽跟普通帽子、兜帽混淆了。把提示词改成 “yellow hard hat on head of a worker” 之后准确率明显上升。提示词不是越长越好但针对性一定要强把目标的场景属性、位置关系、视觉特征都描述进来效果最好。这种提示词的写作逻辑跟我调试开源模型 prompt 的套路是相通的——语义上要跟模型训练语料里常见的视觉表达对齐。调试过程中常用box_threshold和text_threshold这两个阈值。box_threshold控制检测框置信度调低一点0.3 以下可以提升召回但会引入较多误检调高一点0.5 以上更保守适合类别容易混淆的场景。text_threshold控制文本与视觉特征匹配的置信度我一般保持在 0.25-0.3 之间。这两组参数可以直接通过 autodistill 的GroundedSAM传给底层模型也可以在官方推理脚本里调整。3.2 autodistill 的数据流与蒸馏式标注逻辑autodistill 的设计思路可以理解成“大模型打标签小模型学本领”。它天然拆分出两个模型基础模型teacher负责生成标注目标模型student最终要在数据集上训练。整个流程是指定一个包含图片的文件夹让基础模型批量推理生成标注将标注结果与图片一起封装成数据集对象用这个数据集训练目标模型比如 YOLOv8训练完成后后续推理就不再需要基础模型了直接用轻量目标模型这其实是一种知识蒸馏思路的简化落地版它不是让大模型直接喂给小模型特征而是把大模型生成的标注当成标签再用小模型去拟合。这个设计很贴合工业界的用法部署环境跑不动大模型但训练数据可以由大模型批量生产。autodistill 的Dataset对象支持多种格式输出包括 COCO、YOLO、TFRecord 等。我一般习惯先用dataset.export()导出成 COCO再转成 X-AnyLabeling 能打开的格式这样整条流程的衔接最顺。具体转换代码在后面章节会给到。3.3 X-AnyLabeling 的格式兼容性与人工审核效率X-AnyLabeling 是我用下来最顺手的标注工具主要原因在于它支持多种标注格式的读取和保存包含 LabelMe JSON、COCO、YOLO txt、VOC XML 等。更贴心的是它可以读取已有的 LabelMe JSON并将 SAM 的标注结果以 JSON 的形式直接叠加到图像上这意味着自动标注的结果几乎无缝衔接人工审核。标注文件的导入导出一个微型工作量如果格式不兼容整条流水线的价值就大打折扣。X-AnyLabeling 在“格式兼容性”这个维度做得非常到位它甚至支持 YOLOv8 分割格式也就是class_id x1 y1 x2 y2 ... xN yN这种变长格式。我实际测试过把 autodistill 导出的 COCO 转成它的可读格式之后打开、修正、再导出整个过程流畅稳定没有出现过文件损坏或坐标偏移的问题。另一个提升效率的点是内置的交互式分割工具。当自动标注结果不理想需要“抠”出某些轮廓时我可以用它内置的 SAM 交互模型在目标区域点几下就能快速生成新的掩码比手工用多边形慢慢描快得多。这正好跟自动标注形成互补自动标注负责“铺量”人工审核负责“精修”精修过程中再借助 AI 能力提升效率。4. 实操过程从原始图片到可训练数据集4.1 阶段一用 autodistill Grounded-SAM 批量生成初始标注这一步是整个流程中最关键也最高产的部分。我拿“工地安全装备检测”项目来走一遍完整流程。先准备数据把未标注的图片统一放入一个文件夹比如./images/raw。接着创建一个 Python 脚本内容大概这样from autodistill_grounded_sam import GroundedSAM from autodistill.detection import DetectionOntology ontology DetectionOntology.from_string( person. hard hat. safety vest. car. truck. excavator. ) base_model GroundedSAM( ontologyontology, box_threshold0.35, text_threshold0.25 ) dataset base_model.label( input_folder./images/raw, output_folder./datasets/labeled, output_formatcoco )执行之后./datasets/labeled下就会生成 COCO JSON 格式的标注文件和对应的图片。整个批处理过程会自动遍历目标文件夹下的所有图片自动生成标注。这里有个关键点output_formatcoco生成的是单文件 COCO JSON如果你之后要在 X-AnyLabeling 里逐张打开修正可能需要再拆成单张的 LabelMe JSON。我用一个简短脚本做了这个拆分。跑批处理的时候我建议先拿 50 张图试跑把box_threshold和text_threshold调好确认召回率和误检情况在可接受范围再全量跑。如果不调试直接全量跑很可能某个提示词设计不当导致大量图片的标注质量偏低返工成本比手工标注还高。4.2 阶段二COCO JSON 转 X-AnyLabeling 可读的标签文件X-AnyLabeling 原生支持 LabelMe JSON 格式也就是每张图对应一个.json文件结构大致是{ version: 5.2.1, flags: {}, shape: [], imagePath: img001.jpg, imageData: null }autodistill/COCO 输出是集中式的所有标注都集中在annotations数组里。我要把它拆成图片维度的shapes。核心转换逻辑大致是这样def coco_to_labelme(coco_json_path, output_dir): with open(coco_json_path, r) as f: coco json.load(f) images {img[id]: img for img in coco[images]} categories {cat[id]: cat[name] for cat in coco[categories]} for img_id, img in images.items(): labelme_json { version: 5.2.1, flags: {}, shapes: [], imagePath: img[file_name], imageData: None } for ann in coco[annotations]: if ann[image_id] ! img_id: continue category_name categories[ann[category_id]] if segmentation in ann and ann[segmentation]: # 使用分割掩码 shapes.append({ label: category_name, points: 展开多边形坐标, shape_type: polygon, flags: {} }) elif bbox in ann: # 使用检测框转为四点多边形 ... with open(os.path.join(output_dir, img[file_name] .json), w) as f: json.dump(labelme_json, f)展开多边形坐标时要注意坐标系的对应关系。COCO 的 segmentation 坐标是绝对像素坐标而 X-AnyLabeling 的points也是绝对坐标两者直接匹配不用归一化。如果自动检测回来的是检测框而不是多边形我会把矩形框扩展成四边形的四个顶点在 X-AnyLabeling 里再手动细化边缘这样至少位置和大小是对的。这个转换脚本属于典型的“一次性工具”写完跑完就可以扔但代码本身值得好好写因为有大量边界情况需要处理例如空标注的图、segmentation 中带空洞的多边形环、多个标注类别的顺序问题等。4.3 阶段三X-AnyLabeling 人工审核与修正把拆好的 JSON 放进 X-AnyLabeling打开对应的图片就能看到自动标注的结果。我的工作流程是这样的第一遍快速浏览只关注有没有明显的大错误比如完全没有检测出来的目标、检测出的框位置差太远、两个目标被切成同一个掩码等。这类问题直接删掉错误标注或重新用内置 SAM 交互分割重做。第二遍做细修重点是掩码的边界贴合度。建筑工地场景中人穿着反光背心、戴着安全帽SAM 生成的掩码通常具有良好的质量但在遮挡和模糊边界处会有瑕疵比如安全帽的掩码把头发也圈进去了。这时候用 X-AnyLabeling 的多边形编辑工具微调几个顶点就行一张图平均耗时不到 30 秒。熟悉了快捷键之后效率更高我按 Q 切换到选择工具直接拖拽顶点调整。这个环节的核心心态是“只修错误不要过度完美”。自动标注的目标是生成 80 分以上的标签人工把它提升到 95 分以上即可。如果追求每个掩码都是完美的像素级贴合那反而违背了自动标注提效的初衷。4.4 阶段四导出数据并训练目标模型审核完成之后X-AnyLabeling 可以一键导出 YOLO 格式、COCO 格式或者 VOC 格式。我一般导出 YOLO 分割格式因为后续要在 YOLOv8 上训练。导出后可以用 Ultralytics 直接开训配套的代码也很简单from ultralytics import YOLO model YOLO(yolov8s-seg.pt) model.train(datadataset.yaml, epochs100, imgsz640)训练完成后用模型在验证集上评估如果 mAP 低于 0.5我通常会回头检查两方面一是自动标注阶段是否对某些类别产生了系统性的漏检或误检二是人工修正阶段是否漏掉了某些容易混淆的类别。这两个问题反馈到数据层面比盲目调训练参数更管用。5. 常见问题与排查技巧实录5.1 Grounded-SAM 推理速度慢或显存不足症状批处理到一半程序崩溃或者显存占用打满导致卡顿。解决思路分三步走。第一把 SAM 的模型类型从vit_h换成vit_b在 Loading 阶段直接改配置即可。速度提升非常明显1080p 图片从单张约 1.2 秒降到约 0.4 秒显存占用也从 8GB 以上降到 5GB 左右。第二把图片长边缩放到 1280 或 1024SAM 对长边的分辨率上限本来就有约束再高也是等比例缩放不会带来额外精度收益。第三如果仍然爆显存把 batch size 降到 1逐张处理。5.2 检测漏检或误检过多症状某个类别经常没框出来或者框出来后掩码把背景也包进去了。最常见的根因是提示词写得不够准确。可以先针对漏检的样本单独调试提示词在 Grounded-SAM 官方推理脚本里做几次迭代测试。另外就是阈值设置问题把box_threshold降到 0.25 可以明显提升召回但代价是高置信度的误检增多。我们最终用的策略是“用稍低的阈值保证召回用 X-AnyLabeling 人工删除误检”。因为删除误检比补漏检要快得多毕竟误检是少数漏检是万一看漏了就更麻烦。5.3 标注格式转换出错或坐标偏移症状在 X-AnyLabeling 里打开的自动标注结果出现跑偏、错位、比例错误。先检查坐标系COCO 的坐标是绝对像素LabelMe 的坐标也是绝对像素中间没有归一化问题通常出在 JSON 结构不对。仔细检查shapes数组里的points格式是否嵌套正确X-AnyLabeling 需要[[x1, y1], [x2, y2], ...]的形式。如果导出 YOLO 格式后训练报坐标越界错误我记得要去检查是否做了归一化YOLO 分割模式下坐标是归一化到 0-1 之间别忘了除以图像宽高。5.4 autodistill 初始化时网络问题症状首次实例化 GroundedSAM 时卡住或者报网络连接错误。autodistill 首次运行要下载 Grounding DINO 和 SAM 的权重如果网络波动下载会中断导致环境被锁死。我建议提前手动下载权重文件放到~/.cache/autodistill/或者直接改代码里的权重路径。另一个坑是OPENAI_API_KEY缺失时有的 autodistill 版本会在初始化时尝试连接 API 并失败。如果你不想用外部 API可以显式传入空字符串或直接改配置跳过 prompt 优化。5.5 X-AnyLabeling 打开大图或大量文件卡顿症状单张高分辨率图比如 4000x3000打开要好几秒缩放卡顿明显。这是 Qt 渲染大图的通病。我的方法是先用图像预处理脚本把全量图片长边缩放到 1920 左右再进人工审核流程训练时再适配上采样还原尺寸。对于只做检测不做分割的项目1920 的长边足够看清目标标注出来的坐标在训练小模型时完全够用。如果 1920 觉得不够清晰可以提高到 2560但要接受一定的卡顿。6. 最后分享一点我个人的实操心得折腾了这么久的自动标注最大的体会就是不要迷信模型能力也别低估人工审核的价值。Grounded-SAM 确实能生成高质量的初始标注但它对提示词的依赖远超大多数人的预期。提示词设计得好自动标注的质量可以高到几乎不需要修正提示词设计不好效率反而不如直接手工标注。所以我在每个新项目启动时都会专门抽出半天时间测试提示词和阈值把这个基础打好再上量。另一个心得是工具的关联比工具本身更重要。刚开始我只装了 X-AnyLabeling后来才发现它跟 autodistill、Grounded-SAM 可以形成一条完整链路。单独用任何一个工具效率都只是“比手标快一点”但把它们串起来效率就是成倍的提升Grounded-SAM 负责自动生成autodistill 负责批量和格式X-AnyLabeling 负责审核与修正三者无缝衔接之后整个标注流程才真正从“人工绘制”跃进到“人工审阅”。最后一个小技巧每次生成完一批标注都要做一个抽样质检。我会随机抽 5-10% 的图片看一眼标注结果确认没有系统性偏差比如某个类别整体漏检、掩码明显偏大或偏小再进入下一环节。这个习惯帮我挡掉了好几次大事故——有一次提示词没写好整个数据集的“安全帽”类别几乎没有标注出来幸好抽样时发现了省去了后面前功尽弃的代价。自动标注只是一个工具真正决定数据质量的还是你审核的细致程度。
网站建设高端定制企业官网