視頻結構化類應用涉及到的技術棧比較多,而且每種技術入門門檻都較高,比如視頻接入存儲、編解碼、深度學習推理、rtmp流媒體等等。每個環節的水都非常深,單獨拿出來可以寫好幾篇文章,如果沒有個幾年經驗基本很難搞定。本篇文章簡單介紹視頻結構化類應用涉及到的技術棧,以及這類應用常見結構,因為是實時視頻分析,因此這類應用基本都是管道(pipeline)設計模式。本篇文章算是科普入門介紹文章,不涉及詳細技術細節,適合這方面的新手。
所謂視頻結構化,就是利用深度學習技術對視頻進行逐幀分析,解析出視頻幀中感興趣的目標、並且進一步推理出每個目標感興趣的屬性,最后將這些目標、屬性保存成結構化數據(能與每幀關聯起來)。如果是實時類應用,要求實時看到分析結果,那么整個過程要求能做到實時性,比如單路視頻分析保證FPS能達到原視頻的FPS(常見是25)。當然,還有另外一類結構化類應用並不要求做到實時性,比如分析監控錄像,將視頻錄像文件進行結構化處理,結果存於數據庫,用於后期快速檢索,這類應用不用做到實時分析,打個比方,每秒處理25幀和處理5幀對於這類應用影響不大,只是處理完一個錄像文件總耗時不同。本篇文章主要介紹實時(Real-Time)視頻結構化。
上圖中實時將結構化數據疊加在視頻畫面中,圖中紅色多邊形為人工配置檢測區域(ROI),ROI之外的目標可以忽略。
視頻結構化常見Pipeline
視頻從接入,到模型推理,再到結果分析、界面呈現,是一個“流式”處理過程,我們可以稱為pipeline,對於實時視頻結構化類應用,要求整個pipeline各個環節均能滿足性能要求,做到實時處理,某個環節達不到實時性,那么整個pipeline就有問題。下面是我整理出來的視頻結構化處理pipeline,這個設計基本可以滿足要求,有些pipeline可能不長這樣,但是大同小異。
如上圖所示,數據從左往右移動。涉及到的技術有視頻接入、解碼、目標檢測(一次推理)、目標跟蹤、屬性分類(二次推理)、數據分析(目標軌跡分析、目標行為分析、數據存儲)、圖像疊加、編碼、rtmp推流。下面詳細說一下每個環節涉及到的技術內容。
視頻接入
在處理視頻之前,需要先將視頻接入到系統。常見的接入方式有2種,一種就是直接從攝像機(攝像頭)直接接入,常見IP攝像機都支持RTSP/28181國標/設備SDK方式接入;第二種就是從視頻管理平台接入,所謂管理平台,其實就是管理所有的攝像機視頻數據,攝像機先接入平台,其他系統如果需要視頻數據,需要通過SDK/協議再從平台接入,這種方式的好處是平台已經適配了所有前端攝像機,其他系統找平台接入視頻時邏輯更簡單。
解碼
視頻接入到系統之后,緊接着需要做的是解碼,因為后面深度學習推理的輸入是RGB格式的圖片。常見解碼庫可以采用ffmpeg,ffmpeg入門簡單,但是如果想做好、適配實際現場各種情況卻需要很多經驗。解碼環節的輸入輸出如下圖所示:
上圖左邊輸入視頻流二進制數據,經過解碼后,輸出單張RGB圖片序列。
目標檢測(一級推理)
解碼之后得到每幀RGB格式的圖片,將圖片依次輸入目標檢測模型,GPU加速推理后得到每幀中感興趣的目標。這個環節是一次推理,主要作用是從單幀圖像中鎖定感興趣的目標(目標類型、目標可信度、目標位置)。常見目標檢測算法有yolo系列、ssd、rcnn系列。目標檢測環節的輸入輸出如下圖所示:
上圖左邊輸入RGB圖片序列(可以按batch輸入,batch size可以為1),經過目標檢測環節后,輸出每幀中檢測到的目標(類型, 可行度, 目標位置)。
目標跟蹤
目標檢測是單幀處理,視頻幀是連續的,如何將前后幀中的目標一一關聯起來就叫目標跟蹤。目標跟蹤的作用是為了后面的軌跡分析,通過軌跡分析得出目標的行為。目標跟蹤的算法有很多,最簡單最好理解的是IOU方法,通過計算前后幀每兩目標區域之間的IOU來關聯目標,並賦予該目標唯一ID(標識符),之后的軌跡分析全部基於該ID。目標跟蹤環節的輸入輸出如下:
上圖左邊輸入前后兩幀的目標(M*N),經過跟蹤環節后,將M和N個目標一一關聯,賦予目標ID。
屬性分類(二級推理)
對於檢測得到的目標,有可能需要進一步對某些感興趣的屬性進行推理,比如我們檢測到了一輛車,我們需要進一步確認它是什么車(轎車、SUV還是皮卡)?還需要知道該車什么顏色(白色、黑色還是黃色)?因此,對於每個檢測得到的目標,我們需要根據該目標位置(left、top、width、height)裁剪出目標圖像,輸入到第二個模型中進行推理,我們稱之為二次推理。二次推理環節的輸入輸出如下:
上圖左邊輸入檢測到的車輛(根據尺寸位置裁剪,可以按batch輸入,batch size可以為1),經過屬性分類環節后,輸出每個目標的各個屬性值。注意:上圖推理模型為多輸出模型(multi-outputs),可以同時為多個屬性分類。
結果分析
根據具體的業務邏輯,我們可以在這里做一些具體的數據分析,比如根據目標軌跡判斷目標行為是否合法(車輛逆行、車輛停車),根據進入畫面行人特征(年齡、性別、穿着、交通工具)來判斷該目標是否是犯罪嫌疑人(自動告警)。這塊的邏輯根據實際需要可以自行擴展,當然前提是前幾個環節可以產生足夠的數據,比如模型能檢測出來充分的屬性值。
數據持久化
該環節可以將前面產生的結構化數據存入數據庫(可以將其與幀編號關聯起來,或者與視頻時間戳關聯),后面方便快速檢索。同時,通過行為分析環節,如果發現重要結果(比如發現嫌疑人、比如發現有車輛逆行),可以實時上報服務器。
圖像疊加(OSD)
為了便於實時查看畫面分析結果,我們需要在該環節將前面的結構化數據疊加到原始圖片幀上。該環節很簡單,按照數據格式使用opencv等圖像庫將其繪制到圖片即可,同樣我們還可以將目標軌跡疊加在圖片上。
上圖中將前面檢測到的目標,跟蹤軌跡,按照不同的顏色繪制到原始圖片幀上。
編碼 + RTMP推流
圖像疊加之后,只能在本地看效果,實際工程中通常是將疊加之后的圖片序列進行編碼,然后通過rtmp等方式推送到nginx等流媒體服務器,其他用戶可以通過rtmp地址查看實時疊加效果。
上圖中,經過編碼、rtmp推流后,其他用戶可以使用對應地址播放疊加流。