兴趣学习: 人脸识别系统实现 …

人脸识别系统
      这个学期的软件工程作业----人脸识别系统, 基本功能还是实现了, 具体思路从国外一篇博客
学习而得,  http://www.shervinemami.info/faceRecognition.html, 写的非常好. 具体实现的方法呢, 
我就不讲解了, 看了就懂. 需要完整代码可以留言. 还是前面总结的问题"道"与"术"的问题, 学习要
学习解决方法的思路.
 
难点: 人脸库的制作, 人脸的照片需要计算出特征向量, PCA主成分析法. 提高人脸识别精确度需要自己
根据具体情况取照片. 以下是我的读入人脸的train.txt文件(部分). 我用的是每人20张照片, 实验证明
相识度计算出来大概是40%~60%左右.
1 shanghe tt\shanghe\1.jpg
1 shanghe tt\shanghe\2.jpg
1 shanghe tt\shanghe\3.jpg
2 zhijie tt\zijie\1.jpg
2 zhijie tt\zijie\2.jpg
2 zhijie tt\zijie\3.jpg
3 haoru tt\haoru\1.jpg
3 haoru tt\haoru\2.jpg
3 haoru tt\haoru\3.jpg
4 benson tt\jiayong\1.jpg
4 benson tt\jiayong\2.jpg
4 benson tt\jiayong\3.jpg

 
贴一些核心代码:(不完整, 不熟悉的代码不要随便用!!!)

//计算欧拉距离
//寻找最接近的图像
int findNearestNeighbor(float * projectedTestFace)
{
      double leastDistSq = DBL_MAX;    //定义最小距离,并初始化为无穷大
      int i, iTrain, iNearest = 0;
      for(iTrain=0; iTrain
      {
              double distSq=0;
              for(i=0; i
              {
                      float d_i =
                              projectedTestFace[i] -
                              projectedTrainFaceMat->data.fl[iTrain*nEigens + i];
                          distSq += d_i*d_i; // Euclidean算法计算的距离
              }
              if(distSq < leastDistSq)
              {
                      leastDistSq = distSq;
                      iNearest = iTrain;
              }
      }
      fConfidence = 1.0f - sqrt( leastDistSq / (float)(nTrainFaces * nEigens) ) / 255.0f;
      iCount++;
      if( fConfidence > thres )
                      recCount++;
      printf("Confidence = %f\n",fConfidence);
      if(fConfidence < 0.40) return -1;  //根据具体情况设置阀值
      return iNearest;
}
 
//主成分分析
void doPCA()
{
      int i;
      CvTermCriteria calcLimit;
      CvSize faceImgSize;
      // 自己设置主特征值个数
      nEigens = nTrainFaces-1;
      //分配特征向量存储空间
      faceImgSize.width  = faceImgArr[0]->width;
      faceImgSize.height = faceImgArr[0]->height;
      eigenVectArr = (IplImage**)cvAlloc(sizeof(IplImage*) * nEigens);  //分配个数为住特征值个数
      for(i=0; i
              eigenVectArr[i] = cvCreateImage(faceImgSize, IPL_DEPTH_32F, 1);
      //分配主特征值存储空间
      eigenValMat = cvCreateMat( 1, nEigens, CV_32FC1 );
      // 分配平均图像存储空间
      pAvgTrainImg = cvCreateImage(faceImgSize, IPL_DEPTH_32F, 1);
      // 设定PCA分析结束条件
      calcLimit = cvTermCriteria( CV_TERMCRIT_ITER, nEigens, 1);
      // 计算平均图像,特征值,特征向量
      cvCalcEigenObjects(
              nTrainFaces,
              (void*)faceImgArr,
              (void*)eigenVectArr,
              CV_EIGOBJ_NO_CALLBACK,
              0,
              0,
              &calcLimit,
              pAvgTrainImg,
              eigenValMat->data.fl);
      cvNormalize(eigenValMat, eigenValMat, 1, 0, CV_L1, 0);
}
 
//加载txt文件的列举的图像
int loadFaceImgArray(char * filename)
{
      char *faceCascadeFilename = "haarcascade_frontalface_alt2.xml";
      CvHaarClassifierCascade *cascade;
      cascade = (CvHaarClassifierCascade *)cvLoad(faceCascadeFilename,0,0,0);
      CvRect rc;
      FILE * imgListFile = 0;
      char imgFilename[512];
      int iFace, nFaces=0;
      num = 0;
      char temp[512];
      if( !(imgListFile = fopen(filename, "r")) )
      {
              fprintf(stderr, "Can\'t open file %s\n", filename);
              return 0;
      }
      // 统计人脸数
      while( fgets(imgFilename, 512, imgListFile) ) ++nFaces;
      rewind(imgListFile);
      // 分配人脸图像存储空间和人脸ID号存储空间
      faceImgArr              = (IplImage **)cvAlloc( nFaces*sizeof(IplImage *) );
      personNumTruthMat = cvCreateMat( 1, nFaces, CV_32SC1 );
      for(iFace=0; iFace
      {
              // 从文件中读取序号和人脸名称
              fscanf(imgListFile,
                      "%d %s %s", personNumTruthMat->data.i+iFace, temp, imgFilename);
              if( num != *(personNumTruthMat->data.i+iFace) )
              {
                      strcpy(name[num], temp);
                      num = *(personNumTruthMat->data.i+iFace);
              }
              // 加载人脸图像
              faceImgArr[iFace] = cvLoadImage(imgFilename, CV_LOAD_IMAGE_GRAYSCALE);
              if( !faceImgArr[iFace] )
              {
                      fprintf(stderr, "Can\'t load image from %s\n", imgFilename);
                      return 0;
              }
              rc = detectFaceInImage(faceImgArr[iFace], cascade);
              if(rc.width == -1 && rc.height == -1) return -1;
              cvSetImageROI(faceImgArr[iFace], rc);
              IplImage *temp = cvCreateImage(cvSize(200, 250), faceImgArr[iFace]->depth, faceImgArr[iFace]->nChannels);
              cvResize(faceImgArr[iFace], temp, CV_INTER_LINEAR);
              cvResetImageROI(faceImgArr[iFace]);
              faceImgArr[iFace] = processedImage(temp);
        //    faceImgArr[iFace] = cvCloneImage(temp);
      //      cvSaveImage(imgFilename, faceImgArr[iFace]);
              printf("%d\n", iFace+1);
      }
      fclose(imgListFile);
      return nFaces;
}
 
//图片预处理
IplImage* processedImage(IplImage *imageSrc)
{
      IplImage *imageProcessed;
      IplImage *imageGrey;
      if(imageSrc->nChannels == 3)
      {
              imageGrey = cvCreateImage(cvGetSize(imageSrc), IPL_DEPTH_8U, 1);
              cvCvtColor( imageSrc, imageGrey, CV_BGR2GRAY );
      }
      else
      {
              imageGrey = imageSrc;
      }
      imageProcessed = cvCreateImage( cvSize(200, 200), IPL_DEPTH_8U, 1 );
      cvResize(imageGrey, imageProcessed, CV_INTER_LINEAR);
      cvEqualizeHist(imageProcessed, imageProcessed);
      return imageProcessed;
}
 
结果展示:
兴趣学习: <wbr>人脸识别系统实现 <wbr>-- <wbr>成功展示

兴趣学习: <wbr>人脸识别系统实现 <wbr>-- <wbr>成功展示
精确度有80%, 出奇高这次, 呵呵~~可能代码发现我要把它保存好. 这个学期学习opencv还是很好玩的.
自己继续加油吧!!!
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值