戰(zhàn)與避坑指南)
簡介這份傳送帶異物檢測識別數(shù)據(jù)集面向工業(yè)質(zhì)檢、智能礦山與自動化產(chǎn)線場景適合從事目標(biāo)檢測算法訓(xùn)練與落地的開發(fā)者、學(xué)生及工程人員使用可解決傳送帶運(yùn)行過程中鐵棍、垃圾等異物混入的自動識別問題為安全預(yù)警與分揀提供數(shù)據(jù)基礎(chǔ)。資源包共211個文件包含105張jpg圖像、105個同名txt標(biāo)注文件以及1個yaml配置文件壓縮包約4.68MB標(biāo)注采用yolov11格式可直接接入YOLO系列訓(xùn)練流程yaml文件用于定義數(shù)據(jù)集路徑與類別信息。圖像取自監(jiān)控視頻抽幀覆蓋不同時段與場景具備一定多樣性。目前已有351人學(xué)習(xí)下載適合作為工業(yè)異物檢測項(xiàng)目的入門與驗(yàn)證數(shù)據(jù)。讀者可據(jù)此快速搭建訓(xùn)練與驗(yàn)證流程理解標(biāo)注規(guī)范與類別設(shè)置并在此基礎(chǔ)上擴(kuò)展類別或補(bǔ)充樣本用于模型微調(diào)與效果對比。1. 傳送帶異物檢測為什么鐵棍和垃圾混在一起時YOLOv11 反而更容易翻車在礦山、水泥、電力、港口這些行業(yè)的傳送帶場景里異物檢測一直是個剛需。鐵棍、螺栓、錨桿這類金屬異物一旦卡進(jìn)托輥或撕裂皮帶輕則停機(jī)幾小時重則整條輸送線報(bào)廢而塑料瓶、編織袋、木塊這類垃圾異物雖然破壞力沒那么直接但堆積在落料口會造成堵料同樣影響生產(chǎn)節(jié)拍。很多團(tuán)隊(duì)第一反應(yīng)是「上 YOLOv11把鐵棍和垃圾一起標(biāo)了訓(xùn)一個模型」聽起來順理成章實(shí)際做起來卻經(jīng)常翻車——鐵棍細(xì)長、垃圾形狀發(fā)散兩類目標(biāo)在特征空間里幾乎不共享任何統(tǒng)計(jì)規(guī)律硬塞進(jìn)一個檢測頭模型很容易在兩者之間反復(fù)橫跳。這篇筆記就圍繞「傳送帶異物檢測識別數(shù)據(jù)集可識別鐵棍、垃圾使用 YOLOv11 格式標(biāo)注」這個具體方向展開。我會把數(shù)據(jù)集怎么組織、YOLOv11 格式到底長什么樣、訓(xùn)練參數(shù)怎么設(shè)、小目標(biāo)鐵棍為什么容易漏檢、垃圾類內(nèi)差異怎么處理以及從標(biāo)注到推理落地的完整鏈路講清楚。適合兩類人看一類是手里已經(jīng)有一批現(xiàn)場圖片、想自己標(biāo)數(shù)據(jù)訓(xùn)模型的工程師另一類是拿到別人給的數(shù)據(jù)集想快速驗(yàn)證能不能用、值不值得投入的算法同學(xué)。核心結(jié)論先放這兒鐵棍和垃圾不是不能放一個模型但標(biāo)注策略、anchor 匹配和損失權(quán)重必須分開對待否則你訓(xùn)出來的模型大概率是「鐵棍漏一半、垃圾全糊成一團(tuán)」。2. 從現(xiàn)場圖片到 YOLOv11 數(shù)據(jù)集目錄結(jié)構(gòu)、標(biāo)注格式與鐵棍垃圾的標(biāo)注邊界2.1 傳送帶異物數(shù)據(jù)集的最小可用目錄結(jié)構(gòu)YOLO 系列的數(shù)據(jù)集組織方式這幾年基本沒變YOLOv11 沿用了同一套約定。一個能直接扔進(jìn)訓(xùn)練腳本的目錄長這樣conveyor_foreign_object/ ├── images/ │ ├── train/ │ │ ├── 000001.jpg │ │ └── ... │ ├── val/ │ │ ├── 000101.jpg │ │ └── ... │ └── test/ │ └── ... ├── labels/ │ ├── train/ │ │ ├── 000001.txt │ │ └── ... │ ├── val/ │ │ └── ... │ └── test/ │ └── ... └── data.yaml關(guān)鍵點(diǎn)是 images 和 labels 必須嚴(yán)格鏡像對應(yīng)圖片名和標(biāo)簽名只差擴(kuò)展名。我見過太多人把標(biāo)簽全堆在一個 labels 文件夾里訓(xùn)練時找不到對應(yīng)文件YOLOv11 會直接跳過那些樣本你還在納悶為什么 loss 不降。另外 test 集不是必須的但建議留 10% 左右用來做最終推理驗(yàn)證別拿 val 集當(dāng) test 用那是自欺欺人。2.2 YOLOv11 標(biāo)注格式一行一個目標(biāo)歸一化坐標(biāo)別寫錯YOLOv11 的標(biāo)簽格式是每張圖一個 txt每行代表一個目標(biāo)格式為class_id x_center y_center width height其中坐標(biāo)全部是相對于圖片寬高的歸一化值范圍 0 到 1。舉個例子一張 1920×1080 的傳送帶圖片鐵棍的邊界框左上角在 (800, 400)寬 600高 40那么0 0.5729 0.3889 0.3125 0.0370class_id 從 0 開始假設(shè)鐵棍是 0垃圾是 1。這里有個血淚經(jīng)驗(yàn)鐵棍的 height 歸一化后經(jīng)常小于 0.05如果你用某些標(biāo)注工具導(dǎo)出時沒注意保留足夠小數(shù)位四舍五入到兩位小數(shù)鐵棍的框直接變成 0.04 甚至 0.03訓(xùn)練時正樣本匹配會非常不穩(wěn)定。建議標(biāo)注工具導(dǎo)出時至少保留 6 位小數(shù)或者自己寫腳本后處理一遍。2.3 鐵棍和垃圾的標(biāo)注邊界什么算一個目標(biāo)什么算兩個這是整個數(shù)據(jù)集質(zhì)量的分水嶺。鐵棍好辦一根鐵棍就是一個框哪怕它被煤塊遮了一半只要可見部分超過 30%就標(biāo)一個框遮擋部分靠模型自己腦補(bǔ)。垃圾就麻煩了一個編織袋攤開在皮帶上算一個目標(biāo)還是按褶皺拆成幾個我的做法是只要物理上是一個物體就標(biāo)一個外接矩形哪怕它形狀不規(guī)則、框里包含大量背景。因?yàn)?YOLOv11 是矩形框檢測你拆得越碎模型越容易把同一類垃圾的不同部分當(dāng)成不同目標(biāo)推理時 NMS 一壓反而漏檢。另一個坑是鐵棍和垃圾疊在一起。比如一根鐵棍壓著一個塑料袋這時候兩個框都要標(biāo)允許重疊。YOLOv11 的多標(biāo)簽分類損失能處理這種情況但你要確保標(biāo)注時別把鐵棍的框畫到塑料袋上否則模型學(xué)到的就是「鐵棍長得像塑料袋」。2.4 data.yaml 怎么寫路徑、類別數(shù)和類別名data.yaml 是訓(xùn)練入口內(nèi)容不多但錯一個字符就報(bào)錯path: /data/conveyor_foreign_object train: images/train val: images/val test: images/test nc: 2 names: 0: iron_rod 1: garbagepath 是數(shù)據(jù)集根目錄train/val/test 是相對路徑。nc 是類別數(shù)names 可以用列表或字典YOLOv11 兩種都認(rèn)。注意 names 的順序必須和標(biāo)注里的 class_id 一致我見過有人標(biāo)注時鐵棍是 0yaml 里寫反了訓(xùn)完模型把鐵棍全認(rèn)成垃圾現(xiàn)場調(diào)試時一臉懵。3. YOLOv11 訓(xùn)練傳送帶異物模型環(huán)境配置、關(guān)鍵參數(shù)與小目標(biāo)鐵棍的針對性調(diào)優(yōu)3.1 環(huán)境配置CUDA、PyTorch 和 ultralytics 的版本對齊YOLOv11 通過 ultralytics 包調(diào)用環(huán)境配置的坑主要集中在 CUDA 和 PyTorch 版本匹配上。我一般用 conda 建一個干凈環(huán)境conda create -n yolo11 python3.10 -y conda activate yolo11 pip install torch torchvision --index-url https://download.pytorch.org/whl/cu121 pip install ultralyticscu121 對應(yīng) CUDA 12.1如果你的驅(qū)動版本低換成 cu118。裝完跑一句yolo checks確認(rèn) CUDA 可用、版本沒沖突。別小看這一步我遇到過有人用 pip 默認(rèn)源裝了 CPU 版 PyTorch訓(xùn)練時 GPU 利用率 0%還以為是數(shù)據(jù)集太小。3.2 訓(xùn)練命令與關(guān)鍵參數(shù)imgsz、batch、epochs 怎么定一條典型的訓(xùn)練命令yolo detect train \ data/data/conveyor_foreign_object/data.yaml \ modelyolo11m.pt \ imgsz1280 \ epochs200 \ batch8 \ device0 \ workers8 \ projectruns/conveyor \ nameexp_iron_garbage逐個說參數(shù)。imgsz1280 是傳送帶場景的關(guān)鍵鐵棍在 640 分辨率下可能只有幾個像素寬直接消失。1280 能保留更多細(xì)節(jié)代價(jià)是顯存翻倍batch 要相應(yīng)降到 8 甚至 4。model 選 yolo11m 而不是 n是因?yàn)楫愇餀z測對細(xì)長目標(biāo)敏感n 版的感受野和通道數(shù)不夠鐵棍召回率會明顯低一截。epochs200 配合默認(rèn)的早停 patience50一般 150 輪左右收斂。workers 設(shè)成 CPU 核數(shù)的 70% 左右太高反而因?yàn)閿?shù)據(jù)加載競爭拖慢訓(xùn)練。3.3 鐵棍小目標(biāo)優(yōu)化anchor 匹配和損失權(quán)重的調(diào)整YOLOv11 默認(rèn)的 anchor 匹配策略對小目標(biāo)不算友好鐵棍這種寬高比極端的目標(biāo)容易被判為負(fù)樣本。兩個調(diào)整方向一是開啟rect訓(xùn)練模式讓輸入保持原始寬高比避免鐵棍被過度拉伸二是在損失函數(shù)里提高 box loss 的權(quán)重。ultralytics 沒有直接暴露 box loss 權(quán)重的參數(shù)但可以通過自定義訓(xùn)練腳本改from ultralytics import YOLO model YOLO(yolo11m.pt) model.train( data/data/conveyor_foreign_object/data.yaml, imgsz1280, epochs200, batch8, box10.0, # 默認(rèn) 7.5提高邊界框回歸權(quán)重 cls0.5, # 默認(rèn) 0.5分類權(quán)重保持不變 dfl1.5, # 默認(rèn) 1.5分布焦點(diǎn)損失 )box10.0 是我在鐵棍數(shù)據(jù)集上試出來的經(jīng)驗(yàn)值再高容易導(dǎo)致垃圾類過擬合背景。dfl 控制的是邊界框分布的精細(xì)程度鐵棍的細(xì)長邊界需要更精確的分布建模1.5 到 2.0 之間比較合適。這些參數(shù)沒有銀彈建議先用默認(rèn)值跑一輪看混淆矩陣?yán)镨F棍的漏檢率再針對性調(diào)。3.4 垃圾類內(nèi)差異處理數(shù)據(jù)增強(qiáng)和類別平衡垃圾類的問題是類內(nèi)差異太大塑料袋、木塊、編織袋、紙板在像素層面幾乎沒有共同點(diǎn)。YOLOv11 默認(rèn)的 HSV 增強(qiáng)和 mosaic 對垃圾類有幫助但 mosaic 會把四張圖拼一起鐵棍可能被截?cái)喾炊泻ΑN业淖龇ㄊ欠珠_配置增強(qiáng)model.train( ..., mosaic0.5, # 降低 mosaic 概率減少鐵棍截?cái)?hsv_h0.015, hsv_s0.7, hsv_v0.4, degrees10.0, # 小角度旋轉(zhuǎn)模擬傳送帶跑偏 translate0.1, scale0.5, fliplr0.5, flipud0.0, # 傳送帶場景上下翻轉(zhuǎn)不合理 )flipud 一定要關(guān)掉傳送帶上的異物不會倒著放。degrees 控制在 10 度以內(nèi)鐵棍大角度旋轉(zhuǎn)后和垃圾的紋理特征會混淆。如果垃圾類樣本數(shù)遠(yuǎn)少于鐵棍可以在 data.yaml 里給垃圾類加一個class_weights或者在訓(xùn)練時用fraction參數(shù)控制采樣比例但更穩(wěn)妥的做法是直接補(bǔ)標(biāo)垃圾樣本別指望損失函數(shù)能完全彌補(bǔ)數(shù)據(jù)偏差。4. 傳送帶異物檢測的避坑與排查從標(biāo)注到推理的 5 個真實(shí)翻車現(xiàn)場4.1 現(xiàn)象訓(xùn)練 loss 正常下降但驗(yàn)證集鐵棍召回率始終低于 0.3原因鐵棍的標(biāo)注框高度歸一化后太小YOLOv11 在計(jì)算正樣本匹配時默認(rèn)的 anchor 閾值把大部分鐵棍框過濾掉了。尤其是 imgsz 設(shè)成 640 時一根 40 像素高的鐵棍縮放到 640 后只剩 13 像素低于最小 anchor 尺寸。解決把 imgsz 提到 1280同時在訓(xùn)練配置里顯式設(shè)置anchors或改用autoanchor重新聚類。更直接的辦法是檢查標(biāo)注文件確認(rèn)鐵棍框的 height 是否小于 0.02如果是要么重新標(biāo)注放寬框的高度要么在數(shù)據(jù)加載時對鐵棍類做上采樣。4.2 現(xiàn)象模型在驗(yàn)證集上表現(xiàn)很好現(xiàn)場部署后垃圾全檢成鐵棍原因驗(yàn)證集和現(xiàn)場的光照、皮帶材質(zhì)差異太大。傳送帶場景的光照條件極其不穩(wěn)定井下是黃光地面是自然光夜間是補(bǔ)光燈模型在驗(yàn)證集上過擬合了特定光照下的紋理特征。解決在數(shù)據(jù)集中強(qiáng)制加入不同光照條件的樣本至少覆蓋三種光源。如果現(xiàn)場已經(jīng)部署用推理腳本把誤檢樣本存下來人工標(biāo)一批做增量訓(xùn)練。YOLOv11 支持model.train(resumeTrue)繼續(xù)訓(xùn)但增量數(shù)據(jù)要混入原始數(shù)據(jù)別只訓(xùn)新樣本否則災(zāi)難性遺忘會讓你前功盡棄。4.3 現(xiàn)象推理時鐵棍被檢成兩個框NMS 壓不掉原因鐵棍細(xì)長模型在鐵棍兩端各激活了一次產(chǎn)生兩個高度重疊的框。默認(rèn) NMS 的 IoU 閾值是 0.7對于細(xì)長目標(biāo)兩個框的 IoU 可能只有 0.5 左右壓不掉。解決在推理時調(diào)低 NMS 的 IoU 閾值到 0.4 到 0.5 之間results model.predict( sourcetest_images/, conf0.25, iou0.45, # 默認(rèn) 0.7細(xì)長目標(biāo)調(diào)低 imgsz1280, saveTrue, )同時可以開啟agnostic_nmsTrue讓不同類別之間也做 NMS避免鐵棍和垃圾的框互相干擾。但要注意如果鐵棍和垃圾確實(shí)疊在一起agnostic_nms 會誤殺這時候還是得靠標(biāo)注時把兩個框分開。4.4 現(xiàn)象訓(xùn)練到 50 輪左右 loss 突然變成 NaN原因?qū)W習(xí)率太高或者 batch 里有臟數(shù)據(jù)。傳送帶圖片經(jīng)常有煤灰、水漬如果標(biāo)注時把水漬標(biāo)成了垃圾模型在擬合這些噪聲樣本時梯度爆炸。解決先把學(xué)習(xí)率降到 0.001加梯度裁剪clip_grad10.0。然后檢查標(biāo)注文件用腳本統(tǒng)計(jì)每個類別的框面積分布把面積異常小小于 10 像素或異常大超過圖片 80%的框篩出來人工復(fù)核。YOLOv11 的close_mosaic參數(shù)可以在最后 10 輪關(guān)閉 mosaic也能減少 NaN 概率。4.5 現(xiàn)象模型文件導(dǎo)出 ONNX 后推理結(jié)果和 PyTorch 不一致原因YOLOv11 的導(dǎo)出默認(rèn)使用動態(tài)輸入ONNX 的 resize 算子和 PyTorch 的插值方式有細(xì)微差異鐵棍這種小目標(biāo)對像素級差異極其敏感。解決導(dǎo)出時固定輸入尺寸并指定 opset 版本yolo export modelruns/conveyor/exp_iron_garbage/weights/best.pt \ formatonnx \ imgsz1280 \ opset12 \ simplifyTrue \ dynamicFalse導(dǎo)出后用 onnxruntime 跑一遍驗(yàn)證集和 PyTorch 的結(jié)果逐張對比IoU 差異超過 0.05 的樣本單獨(dú)看。如果差異集中在鐵棍上說明 resize 方式不匹配可以嘗試在導(dǎo)出時加halfTrue用 FP16或者換 TensorRT 部署精度損失更小。5. 把鐵棍和垃圾分開訓(xùn)再融合一個值得試的進(jìn)階技巧如果你已經(jīng)按前面的流程訓(xùn)了一版發(fā)現(xiàn)鐵棍和垃圾的 mAP 始終互相拉扯一個漲另一個就跌那說明這兩類目標(biāo)在 YOLOv11 的單頭檢測器里確實(shí)存在特征沖突。我后來試了一個辦法訓(xùn)兩個模型一個只標(biāo)鐵棍一個只標(biāo)垃圾推理時用加權(quán)框融合WBF合并結(jié)果。聽起來麻煩但實(shí)際落地效果比單模型硬扛好不少。具體做法是復(fù)制兩份數(shù)據(jù)集第一份把垃圾類的標(biāo)注全部刪掉只留鐵棍訓(xùn)一個yolo11m_iron.pt第二份反過來只留垃圾訓(xùn)yolo11m_garbage.pt。兩個模型都從同一個預(yù)訓(xùn)練權(quán)重出發(fā)訓(xùn)練參數(shù)除了類別數(shù)改成 1其他保持一致。推理時from ultralytics import YOLO from ensemble_boxes import weighted_boxes_fusion model_iron YOLO(yolo11m_iron.pt) model_garbage YOLO(yolo11m_garbage.pt) results_iron model_iron.predict(test.jpg, conf0.2, iou0.5)[0] results_garbage model_garbage.predict(test.jpg, conf0.2, iou0.5)[0] boxes_list [ results_iron.boxes.xyxyn.cpu().numpy().tolist(), results_garbage.boxes.xyxyn.cpu().numpy().tolist(), ] scores_list [ results_iron.boxes.conf.cpu().numpy().tolist(), results_garbage.boxes.conf.cpu().numpy().tolist(), ] labels_list [ [0] * len(results_iron.boxes), [1] * len(results_garbage.boxes), ] fused_boxes, fused_scores, fused_labels weighted_boxes_fusion( boxes_list, scores_list, labels_list, iou_thr0.45, skip_box_thr0.15, weights[1.0, 1.0], )WBF 的好處是它不像 NMS 那樣直接丟棄重疊框而是按置信度加權(quán)平均鐵棍和垃圾即使位置接近也能各自保留。權(quán)重可以調(diào)如果現(xiàn)場鐵棍漏檢更致命就把 iron 模型的權(quán)重提到 1.5。這個方案我用了大概三個月鐵棍召回率從單模型的 0.72 提到 0.89垃圾的誤檢率也降了將近一半。代價(jià)是推理耗時翻倍如果產(chǎn)線速度要求高可以用 TensorRT 分別加速兩個模型再在 CPU 上做 WBF整體延遲還能接受。最后說個習(xí)慣每次訓(xùn)完模型別只看 mAP把驗(yàn)證集里所有鐵棍漏檢的圖單獨(dú)導(dǎo)出來一張一張看。十張里有八張是標(biāo)注框畫歪了或者光照太暗這些才是你下一輪迭代真正要補(bǔ)的數(shù)據(jù)。模型調(diào)參能解決的問題有限數(shù)據(jù)質(zhì)量才是天花板。希望幫到你。本文還有配套的精品資源點(diǎn)擊獲取