基于Gabor+PCA+SVM的性别识别(3)(完)

基于Gabor+PCA+SVM的性别识别(1): http://www.cnblogs.com/xiaoming123abc/p/5078411.html

基于Gabor+PCA+SVM的性别识别(2): http://www.cnblogs.com/xiaoming123abc/p/5078792.html 

基于前两博文,已经训练出一个性别分类器。那就应该运用这个分类器进行性别分类。

这个测试过程与训练过程一样。只不过,训练时,是大批量的处理样本数据数据。测试过程,针对需要识别的图像进行处理。

  1. 首先进行人脸识别,即在图像中找出人脸,把人脸区域提取出来。
  2. 第二步,运用Gabor小波对人脸提取特征。
  3. 第三步,运用PCA对Gabor提取的特征进行降维处理。
  4. 最后,把降维后特征,输入训练好的分类器,得出分类结果。

结果显示:基于Gabor+PCA+SVM的性别识别(3)(完)_第1张图片

 

基于Gabor+PCA+SVM的性别识别(3)(完)_第2张图片

结果分析:

训练过程man样本 409,woman样本287。其实,对于机器学习来说,这些样本还是很少的。在进行测试时,6个man图像可以正确识别。woman图像识别过程出现了错误识别。因为样本图片都是老外,而且人数有限。对其他图片效果应该不是很好。

本人分析的主要原因有两点:1)在训练过程,Gabor小波、PCA降维过程的参数选取没有进行严格的测试;

                          2)训练样本太少,而且样本中就那几个人的脸。可以增加训练样本的数量。

最后还得提一点,由于训练过程运算量大。训练600多个样本,运行了应该有半个小时。

  main.cpp   (Gabor类文件同(2))               

#include 
#include 
#include 
#include "GaborFR.h"
using namespace cv;
using namespace std;
Mat detectAndDisplay( Mat);
//加载Opencv自带人脸识别级联分类器文件
string face_cascade_name ="D:\\Program Files\\opencv\\sources\\data\\haarcascades\\haarcascade_frontalface_alt.xml";
CascadeClassifier face_cascade;
int iSize=10;//Gabor的scale
int main()
{  
    if( !face_cascade.load( face_cascade_name ) )
      { 
        printf("[error] 无法加载级联分类器文件!\n");
        return -1; 
      }

    Mat testI = imread("man5.png");
    if(testI.data ==0)
       {
          printf("[error] 没有图片\n");
          return -5;
       }
    //提取人脸*****************************************************
     Mat  ROI= detectAndDisplay(testI);
    //Gabor变换*************************************************************
     normalize(ROI,ROI,1,0,CV_MINMAX,CV_32F);
     Mat feature_Gabor;
     feature_Gabor.release();
      for(int i=0;i<8;i++)
    {
        
        for(int j=0;j<5;j++)
        {
            Mat M1= GaborFR::getRealGaborKernel(Size(iSize,iSize),
                                                 2*CV_PI,
                                                 i*CV_PI/8+CV_PI/2,
                                                 j,
                                                 1);
            Mat M2 = GaborFR::getImagGaborKernel(Size(iSize,iSize),
                                                 2*CV_PI,
                                                 i*CV_PI/8+CV_PI/2,
                                                 j,
                                                 1);
            //加了CV_PI/2才和大部分文献的图形一样,不知道为什么!
            Mat outR,outI;
            GaborFR::getFilterRealImagPart(ROI,M1,M2,outR,outI);
            Mat M_Magnitude=GaborFR::getMagnitude(outR,outI);
            normalize(M_Magnitude,M_Magnitude,0,1,CV_MINMAX,CV_32F);
            Mat line= M_Magnitude.reshape(0,1);
            feature_Gabor.push_back(line);
   
        }
    }

//PCA降维**************************************************
    PCA pca(feature_Gabor, cv::Mat(), CV_PCA_DATA_AS_ROW,5);
    Mat dst=pca.project(feature_Gabor) ;
    Mat line =dst.reshape(0,1);

//SVM进行性别识别**************
    CvSVM mySVM; 
    mySVM.load("SVM_PCA4.xml");//从XML文件读取训练好的SVM分类器模型
    float response = mySVM.predict(line );

    cout<< response< faces;
    Mat frame_gray,ROI;
    frame_gray= frame;
    cvtColor( frame, frame_gray, CV_BGR2GRAY );
    equalizeHist( frame_gray, frame_gray );

    face_cascade.detectMultiScale( frame_gray, faces, 1.1, 2, 0|CV_HAAR_SCALE_IMAGE, Size(30, 30) );
    
    for( int i = 0; i < faces.size(); i++ )
    {
        Point center( faces[i].x + faces[i].width*0.5, faces[i].y + faces[i].height*0.5 );
       // ellipse( frame, center, Size( faces[i].width*0.5, faces[i].height*0.5), 0, 0, 360, Scalar( 255, 0, 255 ), 4, 8, 0 );
     rectangle(frame,                //图像.
                 faces[i].tl(),             //矩形的一个顶点。
                 faces[i].br(),             //矩形对角线上的另一个顶点
                 Scalar(0, 255, 0),  //线条颜色 (RGB) 或亮度(灰度图像 )(grayscale image)
                  3);                 //组成矩形的线条的粗细程度。取负值时(如 CV_FILLED)函数绘制填充了色彩的矩形
     ROI=frame_gray(Rect(faces[i].tl().x,faces[i].tl().y,faces[i].width,faces[i].height));
     resize(ROI,ROI,Size(21,18),0,0,CV_INTER_LINEAR);
    }
    
    //namedWindow("qq",2);
    //imshow( "qq", ROI );
   
    imshow( "window_name", frame );
    return ROI;
}


 

    程序下载:http://download.csdn.net/detail/u012507022/9378791

    (VS2010+opencv2.4.11)  

你可能感兴趣的:(Computer,vision)