Haar特征和級聯(lián)分類器目標(biāo)檢測介紹及應(yīng)用
Haar特征和級聯(lián)分類器是一種經(jīng)典的目標(biāo)檢測算法,適用于檢測物體在圖像中的位置、大小和姿態(tài)等。本教程將詳細(xì)介紹Haar特征和級聯(lián)分類器的原理、實(shí)現(xiàn)和應(yīng)用。
1. Haar特征
Haar特征是一種圖像處理中的特征提取方法,用于描述圖像中的紋理、邊緣和線條等特征?;贖aar小波變換的思想,Haar特征將圖像劃分成不同大小、不同形狀的小矩形區(qū)域,對每個區(qū)域內(nèi)的像素進(jìn)行加權(quán)求和得到一個特定的Haar特征值。這些Haar特征值可以作為分類器的輸入,例如在人臉識別中就可以用Haar特征檢測人臉的位置、大小和方向等信息。
Haar特征經(jīng)常用在人臉識別中,它可以通過訓(xùn)練一個分類器來檢測人臉的各種屬性。Haar特征的計算速度相對較快,并且在處理大量數(shù)據(jù)時表現(xiàn)穩(wěn)定,使其成為計算機(jī)視覺領(lǐng)域中比較受歡迎的特征提取方法之一。
2. 級聯(lián)分類器
級聯(lián)分類器(Cascade Classifier)是一種基于Haar特征的對象檢測算法,最早由Paul Viola和Michael Jones在2001年的論文中提出。級聯(lián)分類器主要用于人臉檢測,但也可以用于識別其它物體。級聯(lián)分類器具有高檢測精度和快速檢測速度的特點(diǎn)。
級聯(lián)分類器的實(shí)現(xiàn)依賴于AdaBoost算法。AdaBoost是一種集成學(xué)習(xí)方法,可以將多個弱分類器組合成一個強(qiáng)分類器。級聯(lián)分類器由多個弱分類器組成,每個弱分類器加強(qiáng)一次過濾效果。
級聯(lián)分類器的檢測過程分為多個步驟。首先是圖像預(yù)處理,將圖像轉(zhuǎn)換為灰度圖像,然后進(jìn)行歸一化和直方圖均衡化。接著,級聯(lián)分類器將在圖像的不同位置和不同大小的窗口中,對每個窗口進(jìn)行Haar特征的計算。Haar特征是一種計算圖像中黑白相間矩形框的差值的方法。計算得到的Haar特征值會被送入AdaBoost分類器進(jìn)行分類,如果分類器的輸出值大于預(yù)設(shè)的閾值,則認(rèn)為當(dāng)前窗口中有目標(biāo)物體。如果級聯(lián)分類器中的所有弱分類器都通過了當(dāng)前窗口的驗證,則認(rèn)為整個級聯(lián)分類器檢測到了目標(biāo)物體。
級聯(lián)分類器的訓(xùn)練過程需要大量的正負(fù)樣本。正樣本是指需要檢測的目標(biāo)物體的圖片,而負(fù)樣本是指與目標(biāo)物體相似但不包含目標(biāo)物體的圖片。在訓(xùn)練過程中,級聯(lián)分類器會通過不斷增加弱分類器的數(shù)量和調(diào)整閾值,提高檢測精度。
基于級聯(lián)分類器的人臉檢測系統(tǒng)由若干級聯(lián)分類器組成,每個級聯(lián)分類器的弱分類器數(shù)量和閾值都不同。在每個級聯(lián)分類器中,通過精細(xì)調(diào)整弱分類器的數(shù)量和閾值,使得分類器的檢測精度能夠達(dá)到較高的水平。整個檢測系統(tǒng)的優(yōu)點(diǎn)是快速高效,適合實(shí)時應(yīng)用。
3. 實(shí)現(xiàn)步驟
以下是使用OpenCV實(shí)現(xiàn)Haar特征和級聯(lián)分類器目標(biāo)檢測的基本步驟:
- 收集和準(zhǔn)備訓(xùn)練數(shù)據(jù)。需要使用大量的正樣本和負(fù)樣本,其中正樣本是包含目標(biāo)的圖像區(qū)域,負(fù)樣本是不包含目標(biāo)的圖像區(qū)域。還需要把訓(xùn)練數(shù)據(jù)集劃分為訓(xùn)練集和測試集,并將其分別轉(zhuǎn)換為XML格式。
- 訓(xùn)練級聯(lián)分類器??梢允褂肙penCV提供的trainCascadeClassifier函數(shù)進(jìn)行訓(xùn)練,需要設(shè)置許多參數(shù),如Haar特征的類型和數(shù)量、正負(fù)樣本比例、學(xué)習(xí)率等。訓(xùn)練過程需要一定時間,根據(jù)數(shù)據(jù)集的大小不同可能需要數(shù)個小時到數(shù)天不等。
- 使用級聯(lián)分類器進(jìn)行目標(biāo)檢測。加載訓(xùn)練好的級聯(lián)分類器XML文件,使用OpenCV提供的detectMultiScale函數(shù)對圖像進(jìn)行檢測,會返回檢測到的目標(biāo)位置和大小。
4.嘗試訓(xùn)練自己的級聯(lián)分類器
以下是一個基于OpenCV4的級聯(lián)分類器訓(xùn)練的Python代碼示例,你可以參考這個例子來訓(xùn)練你自己的級聯(lián)分類器。在這個例子中,我們將訓(xùn)練一個可以檢測人臉的級聯(lián)分類器。
首先需要將正負(fù)樣本從數(shù)據(jù)集文件夾中讀入,我們將正樣本命名為"Positive",負(fù)樣本命名為"Negative",在訓(xùn)練級聯(lián)分類器時,需要準(zhǔn)備一些負(fù)樣本。正樣本是需要構(gòu)建檢測器檢測位置的目標(biāo)。
import cv2
import os
# 設(shè)置正負(fù)樣本文件夾路徑
pos_dir = 'Positive/'
neg_dir = 'Negative/'
# 用于存儲正樣本文件名和路徑的列表
pos_files = []
for filename in os.listdir(pos_dir):
if filename.endswith('.jpg'):
pos_files.append(pos_dir + filename)
# 用于存儲負(fù)樣本文件名和路徑的列表
neg_files = []
for filename in os.listdir(neg_dir):
if filename.endswith('.jpg'):
neg_files.append(neg_dir + filename)
# 加載正樣本的圖片
pos_images = []
for file in pos_files:
img = cv2.imread(file, 0) # 將圖片轉(zhuǎn)換為灰度圖像
pos_images.append(img)
# 加載負(fù)樣本的圖片
neg_images = []
for file in neg_files:
img = cv2.imread(file, 0)
neg_images.append(img)
接下來,我們可以定義訓(xùn)練級聯(lián)分類器所需的參數(shù)。這些參數(shù)包括Haar特征的類型和數(shù)量、正負(fù)樣本比例、學(xué)習(xí)率等。這些參數(shù)的設(shè)置不僅受到數(shù)據(jù)集的影響,也需要多次嘗試和優(yōu)化。
# 設(shè)置訓(xùn)練參數(shù)
num_pos = len(pos_images) # 正樣本數(shù)量
num_neg = len(neg_images) # 負(fù)樣本數(shù)量
num_features = 200 # 特征數(shù)量
pos_weight = float(num_neg) / float(num_pos) # 正負(fù)樣本比例
num_stages = 20 # 分類器級聯(lián)層數(shù)
min_hit_rate = 0.995 # 分類器的最小檢測率
max_false_alarm_rate = 0.5 # 最大假陽率
learning_rate = 0.05 # 學(xué)習(xí)率
接下來,我們可以使用trainCascadeClassifier函數(shù)來訓(xùn)練級聯(lián)分類器。在訓(xùn)練過程中,模型會不斷地調(diào)整Haar特征,設(shè)定閾值,去除不必要的特征,最終形成具有適應(yīng)性與推廣性的級聯(lián)分類器。在訓(xùn)練級聯(lián)分類器時,需要耐心等待,可能需要數(shù)小時或更長時間才能訓(xùn)練出一個合適的分類器。
# 訓(xùn)練級聯(lián)分類器
cascade = cv2.CascadeClassifier()
cascade_params = cv2.CascadeClassifier_TrainParams()
cascade_params.featureParams.maxCatCount = 2
cascade_params.featureParams.maxNumFeatures = num_features
cascade_params.featureParams.minNodeSize = (1,1)
cascade_params.featureParams.maxDepth = 1
cascade_params.boostType = cv2.CASCADE_BOOST_REAL
cascade_params.weightTrimRate = 0.95
cascade_params.minHitRate = min_hit_rate
cascade_params.maxFalseAlarmRate = max_false_alarm_rate
cascade_params.stageType = cv2.CASCADE_STAGE_TYPE_HAAR
cascade_params.classifierType = cv2.CASCADE_CLASSIFIER_TYPE_REAL_HAAR
cascade_params.stages = num_stages
cascade_params.weakCount = 100
cascade_params.completeTrainingSet = False
cascade.train(pos_images, neg_images, None, None, cascade_params)
# 保存級聯(lián)分類器
cascade.save('face_cascade.xml')
在訓(xùn)練完成后,級聯(lián)分類器將被保存在當(dāng)前目錄下的face_cascade.xml文件中,可以隨時調(diào)用它進(jìn)行人臉檢測。
4. 應(yīng)用示例
Haar特征和級聯(lián)分類器目標(biāo)檢測算法可以應(yīng)用于很多領(lǐng)域,如人臉檢測、車牌識別、行人檢測等。其中,最為著名的應(yīng)用之一就是OpenCV中的人臉檢測,該算法可以實(shí)現(xiàn)實(shí)時、準(zhǔn)確的人臉檢測,適用于視頻監(jiān)控、自拍美容等應(yīng)用場景。以下是使用OpenCV實(shí)現(xiàn)人臉檢測的代碼示例:
# 導(dǎo)入OpenCV庫和urllib庫
import cv2
import urllib.request
# 設(shè)置圖像 URL 和文件名
url = 'http://www.lenna.org/lena_std.tif'
filename = 'lena.png'
# 通過網(wǎng)絡(luò)下載圖像,并將其保存到本地
urllib.request.urlretrieve(url, filename)
# 讀取圖片并轉(zhuǎn)為灰度圖
img = cv2.imread('lena.jpg') # 讀取圖片文件,返回numpy數(shù)組
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) # 將彩色圖片轉(zhuǎn)換為灰度圖片
# 從GitHub中下載預(yù)訓(xùn)練的人臉分類器XML文件
url = 'https://raw.githubusercontent.com/opencv/opencv/master/data/haarcascades/haarcascade_frontalface_default.xml'
filename = 'haarcascade_frontalface_default.xml' # 聲明下載的文件名
urllib.request.urlretrieve(url, filename) # 將文件從url下載并保存到本地
# 加載預(yù)訓(xùn)練的Haar特征分類器,用于人臉檢測
face_cascade = cv2.CascadeClassifier('haarcascade_frontalface_default.xml')
# 在灰度圖片中檢測人臉
# 參數(shù)1:待檢測圖片,參數(shù)2:縮放比例因子,參數(shù)3:目標(biāo)大小范圍
faces = face_cascade.detectMultiScale(gray, 1.3, 5)
# 在人臉矩形區(qū)域繪制矩形
# 參數(shù)1:需要繪制矩形的圖片,參數(shù)2:矩形左上角的坐標(biāo),參數(shù)3:矩形右下角的坐標(biāo),參數(shù)4:矩形線條顏色,參數(shù)5:矩形線條粗細(xì)
for (x, y, w, h) in faces:
cv2.rectangle(img, (x, y), (x+w, y+h), (0, 255, 0), 2)
# 顯示圖片
# 參數(shù)1:需要顯示的圖片窗口名稱,參數(shù)2:需要顯示的圖片
cv2.imshow('image', img)
cv2.waitKey(0) # 等待用戶按下任意鍵以關(guān)閉窗口
檢測結(jié)果如下所示:
這段代碼的主要作用是使用OpenCV庫實(shí)現(xiàn)人臉檢測,步驟如下:
- 讀取圖片文件,使用cv2.imread()函數(shù)讀取指定路徑下的圖片,返回一個numpy數(shù)組表示該圖片;
- 將彩色圖片轉(zhuǎn)換為灰度圖片,使用cv2.cvtColor()函數(shù)將讀取出來的彩色圖片轉(zhuǎn)換為灰度圖;
- 下載預(yù)訓(xùn)練的人臉分類器XML文件,使用urllib.request.urlretrieve()函數(shù)從GitHub上下載XML文件,保存到本地;
- 加載預(yù)訓(xùn)練的Haar特征分類器,使用cv2.CascadeClassifier()函數(shù)加載XML文件,得到一個分類器對象;
- 在灰度圖片中檢測人臉,使用CascadeClassifier.detectMultiScale()方法對灰度圖片進(jìn)行人臉檢測,返回檢測到的人臉位置;
- 在檢測到的人臉上繪制矩形,使用cv2.rectangle()函數(shù)在原圖片上繪制矩形框,標(biāo)出人臉位置;
- 顯示人臉檢測結(jié)果圖片,使用cv2.imshow()函數(shù)將圖片顯示在窗口中,最后使用cv2.waitKey()函數(shù)等待用戶按下任意鍵,關(guān)閉窗口。
為了使用Python展示Haar檢測中的積分操作,我們可以使用OpenCV庫中的cv2.integral
函數(shù)來計算輸入圖像的積分圖。以下是一個示例代碼,演示如何生成積分圖并將其可視化顯示:
# 導(dǎo)入必要的庫
import cv2
import numpy as np
from matplotlib import pyplot as plt
import urllib.request
# 設(shè)置圖像 URL 和文件名
url = 'http://www.lenna.org/lena_std.tif'
filename = 'lena.png'
# 通過網(wǎng)絡(luò)下載圖像,并將其保存到本地
urllib.request.urlretrieve(url, filename)
# 讀取圖像并轉(zhuǎn)換為灰度圖像
img = cv2.imread('lena.png') # 加載圖像
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) # 轉(zhuǎn)換為灰度圖像
# 計算積分圖
integral_img = cv2.integral(gray) # 計算積分圖
# 顯示原始圖像和對應(yīng)的積分圖
fig, (ax1, ax2) = plt.subplots(ncols=2, figsize=(8, 4)) # 創(chuàng)建子圖
ax1.imshow(cv2.cvtColor(img, cv2.COLOR_BGR2RGB)) # 顯示原始圖像
ax1.set_title('Original Image') # 設(shè)置圖像標(biāo)題
ax2.imshow(integral_img, cmap='gray') # 顯示積分圖
ax2.set_title('Integral Image') # 設(shè)置積分圖標(biāo)題
plt.show() # 輸出圖像
代碼運(yùn)行結(jié)果如下所示:
代碼通過網(wǎng)絡(luò)下載一個名為 lena.png
的圖像文件,并計算了它的積分圖。積分圖是一種預(yù)處理方法,用于在圖像中快速計算子矩形區(qū)域的和。
首先,通過導(dǎo)入必要的庫:cv2
,numpy
、和 matplotlib
來讓這份代碼能夠正常運(yùn)行。并且通過 urllib
模塊,通過給定的圖像 URL 下載圖像并存儲在名為 lena.png
的本地文件中。
然后,使用 cv2.imread
函數(shù)讀入圖像,并使用 cv2.cvtColor
函數(shù)將其轉(zhuǎn)換為灰度圖像,為計算積分圖做準(zhǔn)備。
接下來,使用 cv2.integral
函數(shù)計算灰度圖像的積分圖,并存儲在 integral_img
變量中。
最后,使用 Matplotlib 中的 subplots
函數(shù)創(chuàng)建一個包含兩個子圖的窗口,其中左側(cè)顯示原始圖像,右側(cè)顯示計算得到的積分圖像。在顯示積分圖時,使用 cmap='gray'
參數(shù)將其顯示為灰度圖像。設(shè)置標(biāo)題后,最后顯示窗口中的兩個圖像。
在這個示例中,我們首先讀取了一張圖像,并將其轉(zhuǎn)換為灰度圖像。接著,我們使用cv2.integral
函數(shù)計算輸入圖像的積分圖。積分圖的大小與原始圖像相同,并且每個像素都表示原始圖像中該位置及其左上角的所有像素值的總和。最后,我們使用Matplotlib庫將原始圖像和積分圖在一起可視化顯示出來。可以看到,積分圖中每個位置的值都代表了原始圖像中對應(yīng)位置及其左上角區(qū)域的像素值的總和。文章來源:http://www.zghlxwxcb.cn/news/detail-479375.html
值得注意的是,在Haar特征計算中,積分圖有助于快速計算位于任意矩形區(qū)域內(nèi)的像素值之和,從而避免了對該區(qū)域內(nèi)的每個像素進(jìn)行逐一計算。這可以使Haar特征的計算速度更快。文章來源地址http://www.zghlxwxcb.cn/news/detail-479375.html
到了這里,關(guān)于Haar特征和級聯(lián)分類器目標(biāo)檢測介紹及應(yīng)用的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!