利用OpenCV的Haar特征目标检测方法进行人脸识别的尝试(一)
一、前言
由于還處于學習階段,大多數內容都是從網上學習借鑒的,重復的內容就不多贅述,只是將自己的經驗和想法分享出來。感覺不錯的學習資源如下
http://www.cnblogs.com/tornadomeet/archive/2012/03/28/2420936.html
http://www.cnblogs.com/wengzilin/p/3849118.html
http://blog.csdn.net/liulina603/article/details/8197889
二、目標檢測概念
在實踐前我先閱讀了OpenCV中文網用戶手冊的相關內容,對目標檢測有了一個大體的概念。
鏈接:http://wiki.opencv.org.cn/index.php/Cv模式識別
三、前期準備
1.準備用于人臉識別的正負樣本
樣本的選取上面鏈接的博客中說的都很清楚,按要求選好樣本的大小,比例
需要注意的是。負樣本的選取很有講究,并不是圖片越復雜,圖片之間越不相干越好。如果識別有特定的應用場景,則負樣本中應盡量挑選具有這類特定場景的圖片。當然,我們的人臉識別并沒有特定的場景,盡量選中照相時經常出現的背景即可。另外可以考慮添加一些干擾項,比如動物的臉。
下面是我使用的正負樣本的下載地址,正樣本均標準化為24*24像素,方便大家使用
http://download.csdn.net/detail/u011583927/8534763
2.生成正負樣本的描述文件
按照上面鏈接中的教程一步一步來即可
以正樣本為例,先打開cmd
使用cd 命令將命令行的作用位置調到存放樣本圖像的文件夾下
輸入dir /b >pos_image.txt
正樣本需要將生產的txt文件中數據格式化成固定格式,負樣本不需要
3.創建vec文件
命令:opencv_createsamples.exe -vec pos.vec -info pos_image.txt -bg neg_image.txt -w 24 -h 24 -num 400
四、訓練xml文件
命令:opencv_haartraining.exe -data xml -vec pos.vec -bg neg_image.txt -nstages 20 -nsplits 2 -minhitrate 0.999 -maxfalsealarm 0.5 -npos 800 -nneg 2500 -w 24 -h 24 ?-mem 1024 -mode ALL
訓練的參數進行了多次調整,上面所示是我多次修改后最后選用的。訓練過程可能出現多種多樣的問題,需要耐心的嘗試修改自己的樣本集。如果并沒有達到設置的階段數就停止迭代,并沒有發生錯誤,只是負樣本太少或者不夠豐富。我的就是這種情況,設置的20層,只運行到了14層。這種情況不會自動生成想要的xml文件,需要手動運行
文件夾轉換為xml文件命令:convert.exe --size="24x24" xml haarcascade.xml
convert.exe是opencv自帶的轉換文件,名字應該是convert_cascade。exe
xml是訓練時生成的文件夾的名字
haarcascade.xml是想要生成的xml文件的名字
由于對于算法的理解還不深刻,參數的選擇只是在實踐性的嘗試。
獲得的經驗是影響訓練的效果的最重要環節是樣本的選擇好壞!
首先,在你的精力和時間允許的情況下,收集的樣本越多越好。正樣本好壞會決定人臉的漏識率,負樣本的好壞決定了誤識率。
仔細分析我的樣本可以看出,正樣本800個,是直接下載的人臉包,貌似外國人的人臉居多,可能會影響我們的識別。負樣本2500個,數量較大。
根據我最后的測試結果,和我們的分析是符合的。人臉的漏識率還是不太滿意的,但是誤識率比較低。
訓練了幾個小時,在第13層時停止迭代了,應該是負樣本
五、識別
識別代碼如下,只是簡單調用了openCV提供的函數
#include "cv.h" #include "highgui.h"CvHaarClassifierCascade* load_object_detector( const char* cascade_path ) {return (CvHaarClassifierCascade*)cvLoad( cascade_path ); }void detect_and_draw_objects( IplImage* image,CvHaarClassifierCascade* cascade,int do_pyramids ) {IplImage* small_image = image;CvMemStorage* storage = cvCreateMemStorage(0);CvSeq* faces;int i, scale = 1;/* if the flag is specified, down-scale the 輸入圖像 to get a performance boost w/o loosing quality (perhaps) 如果標識(do_puramids)是指定的,把輸入圖像縮小比例來獲得一個性能的提升 without 不穩定的質量*/if( do_pyramids ){small_image = cvCreateImage( cvSize(image->width/2,image->height/2), IPL_DEPTH_8U, 3 );cvPyrDown( image, small_image, CV_GAUSSIAN_5x5 );/*功能:函數cvPyrDown使用Gaussian金字塔分解對輸入圖像向下采樣。格式:void cvPyrDown(const CvArr*src,CvArr*dst,int filter=CV_GAUSSIAN_5x5);參數:src 輸入圖像。dst 輸出圖像,其寬度和高度應是輸入圖像的一半。filter 卷積濾波器類型,目前僅支持CV_GAUSSIAN_5x5。*/scale = 2;}/* use the fastest variant *//*使用了最快速的檢測方式*/faces = cvHaarDetectObjects( small_image, cascade, storage, 1.1, 2, CV_HAAR_DO_CANNY_PRUNING );/* draw all the rectangles */for( i = 0; i < faces->total; i++ ){/* extract the rectanlges only *///CvRect face_rect = *(CvRect*)cvGetSeqElem( faces, i, 0 );CvRect face_rect = *(CvRect*)cvGetSeqElem( faces, i );cvRectangle( image, cvPoint(face_rect.x*scale,face_rect.y*scale),cvPoint((face_rect.x+face_rect.width)*scale,(face_rect.y+face_rect.height)*scale),CV_RGB(255,0,0), 3 );}if( small_image != image )cvReleaseImage( &small_image );cvReleaseMemStorage( &storage ); } // .exe testImageAddress 分類器地址(xml) /* takes image filename and cascade path from the command line */ int main( int argc, char** argv ) {IplImage* image;if( argc==3 && (image = cvLoadImage( argv[1], 1 )) != 0 ){CvHaarClassifierCascade* cascade=(CvHaarClassifierCascade*)cvLoad(argv[2]);//CvHaarClassifierCascade* cascade = load_object_detector(argv[2]);detect_and_draw_objects( image, cascade, 1 );cvNamedWindow( "test", 0 );cvShowImage( "test", image );cvWaitKey(0);cvReleaseHaarClassifierCascade( &cascade );cvReleaseImage( &image );}return 0; }運行測試文件命令: ?可執行文件地址 圖片地址 xml文件地址
C:\Users\Administrator\Desktop\lena\x64\Debug\lena.exe D:\數字圖像處理\圖像處理圖片\標準測試圖片\dollar.bmp C:\Users\Administrator\Desktop\haarcascade.xml
上傳了幾張程序運行結果
對于比較明顯的人臉,尤其是外國人。。。識別結果還是不錯的
還用了一些生活中的照片,識別效果一般,這里就不上傳了,有一部分臉會漏識,還會偶爾有誤識別。下一步打算把具體的算法深入研究一下,應該會有所突破
總結
以上是生活随笔為你收集整理的利用OpenCV的Haar特征目标检测方法进行人脸识别的尝试(一)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: linux 从光盘安装数据,LINUX访
- 下一篇: ODBG常用快捷键总结