简介:这份资源是中文版 labelImg 1.8.6 免安装包,面向需要做图像标注的算法工程师、数据标注人员以及深度学习入门学习者。解压后直接运行即可使用,省去 Python 环境配置与依赖安装的麻烦,适合目标检测数据集制作、矩形或多边形框标注等场景。压缩包为 rar 格式,共 151 个文件,约 31.63MB,其中以 85 个 dll 与 30 个 pyd 运行库为主,另有 23 个 qm 中文语言文件、7 个 xsl 样式表及 1 个 exe 主程序,整体构成一个可独立运行的标注工具环境。目前已有 2209 人学习下载。工具支持 JPEG、PNG 等常见图像格式,标注结果可导出为 XML,也能转换为 YOLO、CreateML 等格式,方便对接不同检测与分类框架。对于想快速上手标注、减少环境折腾的读者,这份中文汉化版能直接投入数据准备流程,提升标注效率。
1. 中文版 labelImg 1.8.6:打开即用的标注工具到底省掉了哪些事
如果你做过目标检测数据集,大概率在某个深夜被 labelImg 的环境问题卡过:Python 版本不对、PyQt5 装不上、lxml 编译报错、命令行敲进去一堆红字。中文版 labelImg 1.8.6 这个「打开即用,无需安装」的版本,解决的正是这个场景——把 Python 运行时、PyQt5 界面库、lxml 解析库和 labelImg 本体全部打包进一个目录,双击可执行文件就能开始画框。它面向的是需要快速产出 VOC XML 或 YOLO TXT 标注文件的人:算法工程师、数据标注外包管理者、学生做毕设、小团队临时凑数据集。这一章先把「它是什么、省掉了什么、边界在哪」讲清楚,后面几章再拆解目录结构、classes.txt 配置、快捷键流、格式转换和踩坑排查。labelImg 本身是经典的矩形框标注工具,1.8.6 是它较成熟的版本,中文版主要做了界面汉化和打包封装,核心标注逻辑与原版一致。
2. 拆开这个「打开即用」包:目录结构、运行依赖与首次启动
2.1 免安装包到底打包了什么
一个典型的 labelImg 1.8.6 中文免安装包,解压后通常能看到这样的结构。不同打包者命名会有差异,但核心文件跑不出这几类:
| 文件/目录 | 作用 | 是否可删 |
|---|---|---|
| labelImg.exe | 主程序入口,双击启动 | 否 |
| _internal/ 或同级 dll | Python 运行时、PyQt5、lxml 等依赖 | 否 |
| data/predefined_classes.txt | 预定义类别列表 | 可改不可删 |
| libs/ | 图像处理相关库 | 否 |
| README 或 使用说明 | 快捷键和注意事项 | 可删 |
关键点在于:这个包把 CPython 解释器和所有第三方库都塞进了程序目录,运行时不再去系统 PATH 里找 Python。所以你机器上装没装 Python、装的是 3.6 还是 3.11,都不影响它启动。这也是它和pip install labelImg最大的区别——后者依赖你本地的 Python 环境,前者自带环境。
2.2 首次启动的正确姿势与工作目录约定
解压路径建议全英文、无空格,比如D:\tools\labelImg。中文路径在部分 Windows 版本上会导致 Qt 加载资源失败,这是血泪经验。启动前先规划好三个目录:
dataset/ ├── images/ # 存放待标注图片 ├── annotations/ # 存放生成的 XML └── classes.txt # 类别定义文件启动后第一步不是急着画框,而是配置两件事:打开data/predefined_classes.txt,把里面的示例类别改成你自己的,一行一个;然后在界面左侧点「打开目录」选中images/,点「改变存放目录」选中annotations/。这两步做完,后面每张图的标注结果才会自动落到正确位置。
# predefined_classes.txt 示例 person car dog traffic_light提示:classes.txt 里不要留空行,不要用中文逗号分隔,每行一个类别名,顺序会影响 YOLO 格式转换时的 class id。
2.3 界面汉化后的按钮对照与视图模式
中文版把原版的英文按钮做了翻译,但有些翻译和社区教程里的叫法对不上,容易让人懵。对照关系是:「打开」= Open,「打开目录」= Open Dir,「改变存放目录」= Change Save Dir,「创建矩形框」= Create RectBox,「下一张」= Next Image,「上一张」= Prev Image。视图模式有两个:View 菜单里的「显示类别」和「显示框」控制标注框是否可见,新手常误关掉导致以为标注丢了。右侧文件列表会标出哪些图已经标注过,已标注的会显示绿色对勾或不同底色,具体取决于打包版本。
3. 从零标完一批数据:快捷键流、格式选择与批量操作
3.1 画框、改框、删框的完整操作链
标注的核心动作就四个:画框、选类别、保存、下一张。用快捷键能把效率拉满:
W:创建矩形框,鼠标拖拽画框A:上一张图D:下一张图Ctrl+S:保存当前标注Ctrl+D:复制当前框(画同类密集目标时救命)Del:删除选中的框Ctrl+Z:撤销上一步
画完框会弹出类别选择框,从你 predefined_classes.txt 里读出来的列表选。如果列表是空的,说明 classes.txt 没配好或者路径不对,这时候画框会提示你输入类别名,临时输入也能用,但不会自动记忆,下一张还得重输。
3.2 VOC XML 与 YOLO TXT 的切换时机
labelImg 支持两种保存格式,在界面左侧有个格式切换按钮(PascalVOC / YOLO)。这个选择要在开始标注前定好,中途切换会导致已标注文件格式混乱。
PascalVOC 格式生成的是每张图一个 XML,内容长这样:
<annotation> <folder>images</folder> <filename>000001.jpg</filename> <size> <width>1920</width> <height>1080</height> <depth>3</depth> </size> <object> <name>person</name> <bndbox> <xmin>320</xmin> <ymin>180</ymin> <xmax>640</xmax> <ymax>720</ymax> </bndbox> </object> </annotation>YOLO 格式生成的是每张图一个 TXT,每行class_id x_center y_center width height,全部是归一化到 0-1 的值:
0 0.250000 0.416667 0.166667 0.500000选哪个取决于你下游训练框架吃什么。YOLOv5/v8 系列直接吃 YOLO TXT,Faster R-CNN、SSD 这类吃 VOC XML 的多。如果拿不准,先标 VOC,后面用脚本转 YOLO,转换脚本网上一抓一大把,反过来转容易丢精度。
3.3 用脚本批量校验标注结果
标完一批数据,别急着扔进训练。先用脚本做一轮体检,检查有没有空标注、坐标越界、类别名拼写不一致:
import os import xml.etree.ElementTree as ET def check_voc_annotations(anno_dir, img_dir): issues = [] for xml_file in os.listdir(anno_dir): if not xml_file.endswith('.xml'): continue tree = ET.parse(os.path.join(anno_dir, xml_file)) root = tree.getroot() # 检查图片是否存在 img_name = root.find('filename').text if not os.path.exists(os.path.join(img_dir, img_name)): issues.append(f"{xml_file}: 对应图片缺失") objects = root.findall('object') if len(objects) == 0: issues.append(f"{xml_file}: 空标注") for obj in objects: name = obj.find('name').text bbox = obj.find('bndbox') xmin = int(bbox.find('xmin').text) xmax = int(bbox.find('xmax').text) if xmin >= xmax: issues.append(f"{xml_file}: {name} 坐标异常 xmin>=xmax") return issues if __name__ == '__main__': problems = check_voc_annotations('./annotations', './images') for p in problems: print(p) print(f"共发现 {len(problems)} 个问题")这段脚本做三件事:遍历所有 XML、检查对应图片是否存在、检查空标注和坐标逻辑。参数anno_dir和img_dir按你实际目录改。跑完如果输出一堆问题,先别怀疑模型,先把标注质量修了——标注脏数据是训练不收敛的头号玄学来源。
4. 避坑与排查:中文版 labelImg 最容易翻车的五个地方
4.1 双击没反应或闪退
现象:双击 exe 后窗口一闪而过,或者任务管理器里进程出现又消失。
原因:最常见的是解压不完整,杀毒软件把某个 dll 当可疑文件隔离了;其次是路径里有中文或特殊字符,Qt 初始化资源失败。
解决:重新解压,解压时暂时关闭杀毒实时防护;把整个目录挪到纯英文路径下,比如D:\labelImg;如果还不行,用命令行cd到目录后执行labelImg.exe,看控制台报什么错,比双击多一层信息。
4.2 标注保存后找不到 XML 文件
现象:明明按了 Ctrl+S,去 annotations 目录一看是空的。
原因:没有点「改变存放目录」,默认保存路径是程序目录或者上次的路径;或者格式选的是 YOLO,生成的是 TXT 不是 XML。
解决:标注前先确认界面左下角显示的保存路径是不是你想要的;检查格式切换按钮当前是 PascalVOC 还是 YOLO;按 Ctrl+S 后看界面标题栏有没有星号消失,星号消失才代表保存成功。
4.3 类别列表不显示或显示乱码
现象:画框后弹出的类别选择框是空的,或者中文类别显示成方块。
原因:predefined_classes.txt 编码不是 UTF-8,或者文件路径放错了;中文版对中文类别的支持取决于打包时的字体配置,部分精简包会缺中文字体。
解决:用记事本打开 classes.txt,另存为 UTF-8 编码;确认文件在data/目录下;如果中文类别显示乱码,临时改用英文类别名,标注完再用脚本映射回中文,这是最稳的做法。
4.4 大图标注卡顿或画框漂移
现象:标注 4K 以上大图时,鼠标画框和实际落点对不上,或者界面卡成幻灯片。
原因:labelImg 是 Qt 渲染,超大图缩放显示时坐标换算有精度损失;机器显存或内存不足也会导致渲染延迟。
解决:标注前把图片统一缩放到 1920 长边以内,标注完再按比例还原坐标;关闭其他吃内存的程序;如果必须标原图,画完框后放大到 100% 检查一遍边界,别信缩略图上的框。
4.5 多人协作时类别 id 对不上
现象:A 标的数据和 B 标的数据合并后,同一个类别在 YOLO TXT 里 id 不一样,训练时类别错乱。
原因:每个人本地的 classes.txt 顺序不同,YOLO 格式的 class_id 是按 classes.txt 行号来的。
解决:团队统一一份 classes.txt,标注前强制同步;合并数据后用脚本做一次 id 重映射校验;VOC 格式没这个问题,因为存的是类别名不是 id,所以协作场景优先用 VOC 标注,最后统一转 YOLO。
5. 把标注流串成流水线:预标注、格式转换与质量抽检
5.1 用已有模型做预标注再人工修正
纯手工画框在数据量上千后就是体力活。更高效的做法是:先用一个粗糙模型跑一遍推理,把预测框写成 VOC XML,再用 labelImg 打开这些 XML 做人工修正。labelImg 打开目录时会自动加载同名 XML,你只需要拖拽调整框的位置和类别,比从零画快三到五倍。
import xml.etree.ElementTree as ET import os def write_voc_xml(save_path, img_name, img_size, detections): """detections: list of (class_name, xmin, ymin, xmax, ymax)""" root = ET.Element('annotation') ET.SubElement(root, 'filename').text = img_name size = ET.SubElement(root, 'size') ET.SubElement(size, 'width').text = str(img_size[0]) ET.SubElement(size, 'height').text = str(img_size[1]) ET.SubElement(size, 'depth').text = '3' for cls_name, xmin, ymin, xmax, ymax in detections: obj = ET.SubElement(root, 'object') ET.SubElement(obj, 'name').text = cls_name bbox = ET.SubElement(obj, 'bndbox') ET.SubElement(bbox, 'xmin').text = str(int(xmin)) ET.SubElement(bbox, 'ymin').text = str(int(ymin)) ET.SubElement(bbox, 'xmax').text = str(int(xmax)) ET.SubElement(bbox, 'ymax').text = str(int(ymax)) tree = ET.ElementTree(root) tree.write(save_path, encoding='utf-8', xml_declaration=True)这个函数把模型输出的检测框写成 labelImg 能识别的 XML。参数detections里坐标是像素绝对值,img_size是原图宽高。写完的 XML 放到和图片同名的路径下,labelImg 打开目录就会自动加载。注意预标注的框颜色和人工框一样,修正时靠肉眼判断哪些是模型给的、哪些是你改过的,所以建议预标注阶段只保留高置信度框,低置信度的留给人工从零画。
5.2 VOC 转 YOLO 的脚本与三个边界坑
训练前把 VOC 转 YOLO 是标准动作,但转换脚本里有三个坑:
import xml.etree.ElementTree as ET import os def voc_to_yolo(xml_path, classes, img_w, img_h): tree = ET.parse(xml_path) root = tree.getroot() lines = [] for obj in root.findall('object'): cls_name = obj.find('name').text if cls_name not in classes: continue # 坑1:类别不在列表里直接跳过,不报错 cls_id = classes.index(cls_name) bbox = obj.find('bndbox') xmin = float(bbox.find('xmin').text) ymin = float(bbox.find('ymin').text) xmax = float(bbox.find('xmax').text) ymax = float(bbox.find('ymax').text) # 坑2:坐标越界要裁剪 xmin = max(0, min(xmin, img_w)) xmax = max(0, min(xmax, img_w)) ymin = max(0, min(ymin, img_h)) ymax = max(0, min(ymax, img_h)) # 坑3:宽高为0的框要丢弃 w = xmax - xmin h = ymax - ymin if w <= 0 or h <= 0: continue x_center = (xmin + xmax) / 2.0 / img_w y_center = (ymin + ymax) / 2.0 / img_h lines.append(f"{cls_id} {x_center:.6f} {y_center:.6f} {w/img_w:.6f} {h/img_h:.6f}") return lines坑一是类别名拼写不一致时静默跳过,导致某些图标注变少,转换后要统计每类数量对比;坑二是坐标越界,标注时手抖画出图片边界外,不裁剪会导致归一化后值大于1;坑三是零宽高框,通常是误操作产生的,不丢弃会让训练 loss 直接 NaN。这三个坑我在不同项目里各踩过一次,现在转换脚本里默认都加上。
5.3 抽检 5% 数据反查标注一致性
标完几千张图,全检不现实。我的习惯是随机抽 5% 做交叉检查:让另一个人用 labelImg 打开同一批图,只看不标,记录哪些框的类别或边界有明显问题。如果错误率超过 2%,整批返工;低于 2%,针对错误类型做定向修正。这个比例不是拍脑袋,是多次项目里总结出来的——5% 能覆盖大部分系统性错误,又不至于拖慢整体进度。抽检时重点看三类:密集小目标有没有漏标、遮挡目标边界是否合理、类别有没有混淆(比如把「货车」标成「客车」)。这三类错误对模型影响最大,修起来也最值。
希望帮到你。
本文还有配套的精品资源,点击获取