OpenCV-Python教程:45.背景去除

基礎(chǔ)

背景去除是在很多視覺(jué)應(yīng)用里的主要預(yù)處理步驟。例如,攝像這樣的場(chǎng)景。一個(gè)固定攝像頭對(duì)顧客進(jìn)行計(jì)數(shù),或者交通攝像頭對(duì)汽車(chē)信息進(jìn)行提取。在所有這些情況下,首先你需要把人或者車(chē)輛單獨(dú)提取出來(lái)。技術(shù)上你需要從靜態(tài)背景里把移動(dòng)的前景提取出來(lái)。

如果你有一個(gè)單獨(dú)的背景的圖像,比如沒(méi)有顧客的房子的圖像,或者沒(méi)有汽車(chē)的路的圖像,這就很簡(jiǎn)單了。值需要在新的圖像里把背景去掉就行了。你得到的就是前景。但是在大多數(shù)情況下,你可能沒(méi)有這種圖像,所以我們需要從我們有的圖像里把背景去掉。當(dāng)車(chē)有影子的時(shí)候這個(gè)情況就很復(fù)雜了。因?yàn)橛白右苍趧?dòng)。簡(jiǎn)單的去除會(huì)把影子也作為前景。

一些算法來(lái)做這個(gè),OpenCV實(shí)現(xiàn)了三個(gè)這樣的算法,很易用,我們一個(gè)個(gè)看一下。

BackgroundSubtractorMOG

這是一個(gè)高斯混合背景/前景分割算法。它使用一個(gè)方法通過(guò)K高斯分布的混合來(lái)給每個(gè)背景像素建模(K=3到5)?;旌系臋?quán)重表示那些顏色留在場(chǎng)景中的時(shí)間規(guī)模。可能的背景顏色是那些留的時(shí)間更長(zhǎng)更靜止的。

寫(xiě)代碼時(shí),我們使用函數(shù)cv2.createBackgroundSubtractorMOG()創(chuàng)建一個(gè)背景對(duì)象.它有一些可選的參數(shù),比如歷史長(zhǎng)度,高斯混合數(shù)量,閾值等。它們?nèi)际悄J(rèn)值,然后在視頻循環(huán)里,使用backgroundsubtractor.apply()方法來(lái)得到背景掩圖

看一個(gè)簡(jiǎn)單例子:

import numpy as np
import cv2

cap = cv2.VideoCapture('vtest.avi')

fgbg = cv2.createBackgroundSubtractorMOG()

while(1):
? ? ret, frame = cap.read()

? ? fgmask = fgbg.apply(frame)

? ? cv2.imshow('frame',fgmask)
? ? k = cv2.waitKey(30) & 0xff
? ? if k == 27:
? ? ? ? break

cap.release()
cv2.destroyAllWindows()

BackgroundSubtractorMOG2

這也是高斯混合模型的前景/背景分割算法,這個(gè)算法的一個(gè)重要特點(diǎn)是它為每個(gè)像素選擇一個(gè)合適的高斯分布數(shù)。(記住,在上個(gè)例子,我們用了一個(gè)K高斯分布)它提供了更好的由于光照變化因素導(dǎo)致場(chǎng)景變化的適應(yīng)性。

在前面的例子里,我們得創(chuàng)建一個(gè)背景去除對(duì)象,這里,你可以選擇是否檢測(cè)影子。如果detectShadows = True(默認(rèn)的),它會(huì)檢測(cè)并標(biāo)記影子,但是會(huì)減低速度,Shadows會(huì)被標(biāo)記成灰色。

import numpy as np
import cv2

cap = cv2.VideoCapture('vtest.avi')

fgbg = cv2.createBackgroundSubtractorMOG2()

while(1):
? ? ret, frame = cap.read()

? ? fgmask = fgbg.apply(frame)

? ? cv2.imshow('frame',fgmask)
? ? k = cv2.waitKey(30) & 0xff
? ? if k == 27:
? ? ? ? break

cap.release()
cv2.destroyAllWindows()


BackgroundSubtractorGMG

這個(gè)算法合并了統(tǒng)計(jì)背景圖像判斷和每像素貝葉斯分割。

它使用最開(kāi)始的一些幀(默認(rèn)120)來(lái)對(duì)背景建模。它使用概率前景分割算法通過(guò)貝葉斯推論識(shí)別可能的前景物體。判斷是能適應(yīng)的。最新發(fā)現(xiàn)的權(quán)重更好,以適應(yīng)光線變化。一些形態(tài)學(xué)過(guò)濾運(yùn)算比如開(kāi)和閉被使用來(lái)去掉不需要的噪點(diǎn)。你會(huì)在最開(kāi)始的一些幀里得到一個(gè)黑色窗口

最好是通過(guò)形態(tài)學(xué)的開(kāi)運(yùn)算對(duì)結(jié)果使用,來(lái)移除噪點(diǎn)。

import numpy as np
import cv2

cap = cv2.VideoCapture('vtest.avi')

kernel = cv2.getStructuringElement(cv2.MORPH_ELLIPSE,(3,3))
fgbg = cv2.createBackgroundSubtractorGMG()

while(1):
? ? ret, frame = cap.read()
? ?
? ? fgmask = fgbg.apply(frame)
? ? fgmask = cv2.morphologyEx(fgmask, cv2.MORPH_OPEN, kernel)

? ? cv2.imshow('frame',fgmask)
? ? k = cv2.waitKey(30) & 0xff
? ? if k == 27:
? ? ? ? break

cap.release()
cv2.destroyAllWindows()

結(jié)果

原始幀:


BackgroundSubtractorMOG的結(jié)果


BackgroundSubtractorMOG2的結(jié)果

灰色區(qū)域顯示了影子區(qū)域


BackgroundSubtractorGMG的結(jié)果

用形態(tài)學(xué)開(kāi)運(yùn)算去掉了噪點(diǎn)

END

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容