LeRobot已成為機器人學習數據的主要開放格式,但處理其數據並不容易:解碼幀既昂貴又佔用內存,而在GPU閒置時,解碼、轉換和註釋幀的步驟常常成為流水線的瓶頸。為此,我們最近在Daft中引入了原生LeRobot讀取器(Daft #7090),通過daft.datasets.lerobot可直接從Hugging Face讀取數據集為數據幀,每行一幀,並使用load_video_frames將每個攝像頭的視頻解碼為圖像列。
然而,初始版本的速度非常慢。問題在於:每個幀都要遠程打開一次文件。LeRobot v3數據集將每個攝像頭的視頻存儲為MP4分片——這些文件將多個片段的幀打包在一起。解碼一個幀時,讀取器需要打開分片並尋址到該幀的時間戳。打開MP4還需要讀取其索引(即映射時間戳到字節位置的元數據),然後才能進行尋址。原始讀取器逐幀執行此操作:每個幀都重新打開其分片,每次打開都通過網絡重新讀取索引。對於遠程數據集,這大約需要每幀3秒,而且總成本隨幀數線性增長——即使連續行需要來自同一文件的相鄰幀。
修復方法是批量解碼。現在解碼是一個批量UDF(Daft #7184):函數一次接收16個連續行,而不是逐行調用,從而可以跨行規劃解碼。每個批次執行三個步驟:首先,按分片分組行;其次,排序和聚類目標時間戳(10秒內的目標歸為一簇);最後,每個聚類只進行一次尋址和一次前向解碼。尋址到聚類中最早目標的前一個關鍵幀,然後持續解碼,將每個解碼幀與聚類中的目標比較,保留最接近的幀,直到超過最後一個目標為止。
結果令人印象深刻:從遠程數據集解碼8幀從25秒降至3.9秒,成本曲線從線性變為平坦。在六個公共LeRobot v3數據集上,批量讀取器速度提升4-13倍。在1080p數據集上,解碼全部632幀從29分鐘降至不到2分鐘——提升了15倍。此外,在一個基於此讀取器的手部追蹤流水線中,解碼12個遠程幀並運行MediaPipe手部追蹤,端到端時間從44.8秒降至9.8秒,檢測結果完全一致。
要嘗試此功能,只需幾行代碼。使用daft.datasets.lerobot讀取數據集,並指定加載視頻幀的攝像頭。該讀取器僅需一次分片打開即可解碼顯示的行。完整的註釋流水線可參考daft-physical-ai,基準測試結果可在Daft倉庫的benchmarking/lerobot中找到。