本文主要介紹下opencv中怎樣使用hog算法,因為在opencv中已經集成了hog這個類。其實使用起來是很簡單的,從后面的代碼就可以看出來。本文參考的資料為opencv自帶的sample。
關於opencv中hog的源碼分析,可以參考本人的另一篇博客:opencv源碼解析之(6):hog源碼分析
開發環境:opencv2.4.2+Qt4.8.2+ubuntu12.04+QtCreator2.5.
實驗功能:
單擊Open Image按鈕,選擇需要進行人檢測的一張圖片,確定后自動顯示出來。該圖片的大小沒限制。
單擊People Detect按鈕,則程序會自動對該圖片進行行人檢測,且將檢測到的效果顯示出來,即用1個矩形框將行人框出來。
單擊Close按鈕,退出程序。
實驗說明:
1. hog描述子在opencv中為HOGDescriptor。
2. 可以調用該描述子setSVMDetector方法給用於對hog特征進行分類的svm模型的系數賦值,這里的參數為HOGDescriptor::getDefaultPeopleDetector()時表示采用系統默認的參數,因為這些參數是用很多圖片訓練而來的。
3. 對輸入圖片進行行人檢測時由於圖片的大小不一樣,所以要用到多尺度檢測。這里是用hog類的方法detectMultiScale。參數解釋如下:
HOGDescriptor::detectMultiScale(const GpuMat& img, vector<Rect>& found_locations, doublehit_threshold=0, Size win_stride=Size(), Size padding=Size(), double scale0=1.05, int group_threshold=2)
該函數表示對輸入的圖片img進行多尺度行人檢測 img為輸入待檢測的圖片;found_locations為檢測到目標區域列表;參數3為程序內部計算為行人目標的閾值,也就是檢測到的特征到SVM分類超平面的距離;參數4為滑動窗口每次移動的距離。它必須是塊移動的整數倍;參數5為圖像擴充的大小;參數6為比例系數,即滑動窗口每次增加的比例;參數7為組閾值,即校正系數,當一個目標被多個窗口檢測出來時,該參數此時就起了調節作用,為0時表示不起調節作用。
4. 最后對檢測出來的目標矩形框,要采用一些方法處理,比如說2個目標框嵌套着,則選擇最外面的那個框。 5. 因為hog檢測出的矩形框比實際人體框要稍微大些,所以需要對這些矩形框大小尺寸做一些調整。
實驗結果: 圖片1效果:
圖片2效果:
圖片3效果:
圖片4效果:
實驗主要部分代碼(附錄有工程code下載鏈接):
#include "dialog.h" #include "ui_dialog.h" #include <QtCore> #include <QtGui> Dialog::Dialog(QWidget *parent) : QDialog(parent), ui(new Ui::Dialog) { ui->setupUi(this); } Dialog::~Dialog() { delete ui; } void Dialog::on_openButton_clicked() { QString img_mame = QFileDialog::getOpenFileName(this, "Open img", "../people", tr("Image Files(*.png *.jpg *.bmp *.jpeg)")); img = imread( img_mame.toAscii().data() ); imwrite("../hog_test.jpg", img); ui->textBrowser->setFixedSize(img.cols, img.rows); ui->textBrowser->append("<img src=../hog_test.jpg>"); } void Dialog::on_detectButton_clicked() { vector<Rect> found, found_filtered; cv::HOGDescriptor people_dectect_hog; //采用默認的已經訓練好了的svm系數作為此次檢測的模型 people_dectect_hog.setSVMDetector(cv::HOGDescriptor::getDefaultPeopleDetector()); //對輸入的圖片img進行多尺度行人檢測 //img為輸入待檢測的圖片;found為檢測到目標區域列表;參數3為程序內部計算為行人目標的閾值,也就是檢測到的特征到SVM分類超平面的距離; //參數4為滑動窗口每次移動的距離。它必須是塊移動的整數倍;參數5為圖像擴充的大小;參數6為比例系數,即測試圖片每次尺寸縮放增加的比例; //參數7為組閾值,即校正系數,當一個目標被多個窗口檢測出來時,該參數此時就起了調節作用,為0時表示不起調節作用。 people_dectect_hog.detectMultiScale(img, found, 0, Size(8, 8), Size(32, 32), 1.05, 2); //從源碼中可以看出: //#define __SIZE_TYPE__ long unsigned int //typedef __SIZE_TYPE__ size_t; //因此,size_t是一個long unsigned int類型 size_t i, j; for (i = 0; i < found.size(); i++ ) { Rect r = found[i]; //下面的這個for語句是找出所有沒有嵌套的矩形框r,並放入found_filtered中,如果有嵌套的 //話,則取外面最大的那個矩形框放入found_filtered中 for(j = 0; j <found.size(); j++) if(j != i && (r&found[j])==r) break; if(j == found.size()) found_filtered.push_back(r); } //在圖片img上畫出矩形框,因為hog檢測出的矩形框比實際人體框要稍微大些,所以這里需要 //做一些調整 for(i = 0; i <found_filtered.size(); i++) { Rect r = found_filtered[i]; r.x += cvRound(r.width*0.1); r.width = cvRound(r.width*0.8); r.y += cvRound(r.height*0.07); r.height = cvRound(r.height*0.8); rectangle(img, r.tl(), r.br(), Scalar(0, 255, 0), 3); } imwrite("../hog_test_result.jpg", img); ui->textBrowser->clear(); ui->textBrowser->append("<img src=../hog_test_result.jpg>"); } void Dialog::on_closeButton_clicked() { close(); }
實驗總結: 從實驗的結果來看,圖片檢測的准確率一般,當人體遮擋情況比較嚴重,且背景比較復雜時,有些誤檢和漏檢。不過程序的檢查速度還行,因為源碼中用做了些優化處理。