Dlib机器学习库系列2----人脸检测

这是Dlib库学习系列的第二篇,主要介绍人脸检测。Dlib库的人脸检测算法使用的hog特征与级联分类器。废话少说,下面开始。
步骤一:建立工程,配置工程。
建立工程就不多说了,不用预编译头,建立一个空项目就可以。下面主要说配置。
(1)属性->VC++目录
(2)这里写图片描述
(3)就是把上一篇博客中生成的dlib.lib导入工程中
步骤二:编写代码
在此我使用的dlib库提供的例子,我只是增加了中文注释

// The contents of this file are in the public domain. See LICENSE_FOR_EXAMPLE_PROGRAMS.txt
/*


This example program shows how to find frontal human faces in an image.  In
particular, this program shows how you can take a list of images from the
command line and display each on the screen with red boxes overlaid on each
human face.
检测正脸,可检测一系列的图片上的人脸并用红色方框表示


The examples/faces folder contains some jpg images of people.  You can run
this program on them and see the detections by executing the following command:
./face_detection_ex faces/*.jpg  可以使用此命令运行该程序



This face detector is made using the now classic Histogram of Oriented
Gradients (HOG) feature combined with a linear classifier, an image pyramid,
and sliding window detection scheme.  This type of object detector is fairly
general and capable of detecting many types of semi-rigid objects in
addition to human faces.  Therefore, if you are interested in making your
own object detectors then read the fhog_object_detector_ex.cpp example
program.  It shows how to use the machine learning tools which were used to
create dlib's face detector.



Finally, note that the face detector is fastest when compiled with at least
SSE2 instructions enabled.  So if you are using a PC with an Intel or AMD
chip then you should enable at least SSE2 instructions.  If you are using
cmake to compile this program you can enable them by using one of the
following commands when you create the build project:
cmake path_to_dlib_root/examples -DUSE_SSE2_INSTRUCTIONS=ON
cmake path_to_dlib_root/examples -DUSE_SSE4_INSTRUCTIONS=ON
cmake path_to_dlib_root/examples -DUSE_AVX_INSTRUCTIONS=ON
This will set the appropriate compiler options for GCC, clang, Visual
Studio, or the Intel compiler.  If you are using another compiler then you
need to consult your compiler's manual to determine how to enable these
instructions.  Note that AVX is the fastest but requires a CPU from at least
2011.  SSE4 is the next fastest and is supported by most current machines.
*/



#include <dlib/image_processing/frontal_face_detector.h>
#include <dlib/gui_widgets.h>
#include <dlib/image_io.h>
#include <iostream>


using namespace dlib;
using namespace std;


// ----------------------------------------------------------------------------------------


int main(int argc, char** argv)
{
    try
    {
        if (argc == 1)
        {
            cout << "Give some image files as arguments to this program." << endl;
            return 0;
        }


        frontal_face_detector detector = get_frontal_face_detector();//定义一个frontal_face_detctor类的实例detector,用get_frontal_face_detector函数初始化该实例
        image_window win;//一个显示窗口


        // Loop over all the images provided on the command line.
        // 循环所有的图片
        for (int i = 1; i < argc; ++i)
        {
            cout << "processing image " << argv[i] << endl;
            array2d<unsigned char> img;
            load_image(img, argv[i]);// 加载一张图片,从argv[i](图片路劲)加载到变量img
            // Make the image bigger by a factor of two.  This is useful since
            // the face detector looks for faces that are about 80 by 80 pixels
            // or larger.  Therefore, if you want to find faces that are smaller
            // than that then you need to upsample the image as we do here by
            // calling pyramid_up().  So this will allow it to detect faces that
            // are at least 40 by 40 pixels in size.  We could call pyramid_up()
            // again to find even smaller faces, but note that every time we
            // upsample the image we make the detector run slower since it must
            // process a larger image.
            /*确保检测图片是检测器的两倍。这第一点是十分有用的,因为脸部检测器搜寻的人脸大小是80*80或者更大。
            因此,如果你想找到比80*80小的人脸,需要将检测图片进行上采样,我们可以调用pyramid_up()函数。
            执行一次pyramid_up()我们能检测40*40大小的了,如果我们想检测更小的人脸,那还需要再次执行pyramid_up()函数。
            注意,上采样后,速度会减慢!*/
            pyramid_up(img);//对图像进行上采用,检测更小的人脸


            // Now tell the face detector to give us a list of bounding boxes
            // around all the faces it can find in the image.
            //开始检测,返回一系列的边界框
            std::vector<rectangle> dets = detector(img);//detector()函数检测人脸,返回一系列边界盒子


            cout << "Number of faces detected: " << dets.size() << endl;//dets.size 人脸数量
            // Now we show the image on the screen and the face detections as
            // red overlay boxes.
            // 在原图片上显示结果
            win.clear_overlay();
            win.set_image(img);
            win.add_overlay(dets, rgb_pixel(255, 0, 0));


            cout << "Hit enter to process the next image..." << endl;
            cin.get();
        }
    }
    catch (exception& e)
    {
        cout << "\nexception thrown!" << endl;
        cout << e.what() << endl;
    }
}


// ----------------------------------------------------------------------------------------



(2)这个代码是带参主函数,我们可以编译完后用命令行的形式运行。如果你不想那么麻烦,我们可以在属性里设置命令参数
这里写图片描述


做完这一切,编译运行就可以了。


注意!!!
 如果有如下报错1>dlib.lib(base_widgets.obj) : error LNK2038: 检测到“_ITERATOR_DEBUG_LEVEL”的不匹配项: 值“2”不匹配值“0”(dlib_face.obj 中)
 1>dlib.lib(base_widgets.obj) : error LNK2038: 检测到“RuntimeLibrary”的不匹配项: 值“MDd_DynamicDebug”不匹配值“MD_DynamicRelease”(dlib_face.obj 中)
 原因是,你生成的dlib.lib是debug版本,而你的工程建立的是release版本,所有会有这个包括,只要将两者保持一致,就没有在这个报错了! Dlib机器学习库系列2----人脸检测


最近在做人脸识别,其中用到了Dlib库中人脸检测和人脸对齐,因此写下这个系列博客,以备后用。
这篇主要是编译和安装,最终目的是编译出dilb.lib,这样就可以将该静态库添加到我们自己的工程,供我们使用。
步骤一:下载Dlib库
下载链接: http://dlib.net/
这里写图片描述
可以看到网站上还提供了了C++与 Python的例程。
步骤二:用CMake制作dilb.lib
这里写图片描述
配置好路径后,点击1,会提示你选择编译器,按照你的需求选择就可以。前提是你的电脑必须安装,比如你想编译VS2013X64,你必须安装VS2013.然后点击2.等待即可。
如果你以为这样就OK,那就错了,以上只是将Dlib转换成了一个VS工程,我们还需要打开VS,生成这个工程。
步骤三:生成dlib.lib
打开F:/dlibbuild2013x64(这是我的保存路劲,请换成你自己的),找到Project.sln,打开后
这里写图片描述
根据你的需要选择Debug或Release,win32或X64
右击ALL_BUILD->重新生成。等待编译好后在F:/dlibbuild2013x64 里多出两个两个文件夹Debug和x64,dlib.lib在Debug文件夹里。导入自己的工程就OK了!
详细步骤可参考: http://jingyan.baidu.com/article/48b37f8d0461831a6464889c.html
Dlib机器学习库学习系列三----人脸对齐(特征点检测)
步骤一:建立并配置工程,参照上一篇博客。

     步骤二:下载形状模型文件

     下载地址:模型文件

         步骤三:具体代码,这段代码也是dlib提供的例子,我自己添加的中文注释!





[cpp] view plain copy

 01.// The contents of this file are in the public domain. See LICENSE_FOR_EXAMPLE_PROGRAMS.txt 
02./*
03.
04.This example program shows how to find frontal human faces in an image and
05.estimate their pose.  The pose takes the form of 68 landmarks.  These are
06.points on the face such as the corners of the mouth, along the eyebrows, on
07.the eyes, and so forth.
08.****这个例子展示了怎样在一张图片中找到正脸和他们的姿势.姿势是由68个点的形式组成的.
09.
10.
11.//This face detector is made using the classic Histogram of Oriented
12.Gradients (HOG) feature combined with a linear classifier, an image pyramid,
13.and sliding window detection scheme.//
14.****人脸检测器的原理
15.
16.The pose estimator was created by
17.using dlib's implementation of the paper://根据这篇论文编写的程序
18.One Millisecond Face Alignment with an Ensemble of Regression Trees by
19.Vahid Kazemi and Josephine Sullivan, CVPR 2014
20.and was trained on the iBUG 300-W face landmark dataset.
21.
22.Also, note that you can train your own models using dlib's machine learning
23.tools.  See train_shape_predictor_ex.cpp to see an example.
24.****我们可以训练自己的模型,用train_shape_predictor_ex.exe
25.
26.
27.Finally, note that the face detector is fastest when compiled with at least
28.SSE2 instructions enabled.  So if you are using a PC with an Intel or AMD
29.chip then you should enable at least SSE2 instructions.  If you are using
30.cmake to compile this program you can enable them by using one of the
31.following commands when you create the build project:
32.cmake path_to_dlib_root/examples -DUSE_SSE2_INSTRUCTIONS=ON
33.cmake path_to_dlib_root/examples -DUSE_SSE4_INSTRUCTIONS=ON
34.cmake path_to_dlib_root/examples -DUSE_AVX_INSTRUCTIONS=ON
35.This will set the appropriate compiler options for GCC, clang, Visual
36.Studio, or the Intel compiler.  If you are using another compiler then you
37.need to consult your compiler's manual to determine how to enable these
38.instructions.  Note that AVX is the fastest but requires a CPU from at least
39.2011.  SSE4 is the next fastest and is supported by most current machines.
40.*/ 
41. 
42. 
43.#include <dlib/image_processing/frontal_face_detector.h> 
44.#include <dlib/image_processing/render_face_detections.h> 
45.#include <dlib/image_processing.h> 
46.#include <dlib/gui_widgets.h> 
47.#include <dlib/image_io.h> 
48.#include <iostream> 
49. 
50.using namespace dlib; 
51.using namespace std; 
52. 
53.// ---------------------------------------------------------------------------------------- 
54. 
55.int main(int argc, char** argv) 
56.{ 
57.    try 
58.    { 
59.        // This example takes in a shape model file and then a list of images to 
60.        // process.  We will take these filenames in as command line arguments. 
61.        // Dlib comes with example images in the examples/faces folder so give 
62.        // those as arguments to this program. 
63.        // 这个例子需要一个形状模型文件和一系列的图片. 
64.        if (argc == 1) 
65.        { 
66.            cout << "Call this program like this:" << endl; 
67.            cout << "./face_landmark_detection_ex shape_predictor_68_face_landmarks.dat faces/*.jpg" << endl; 
68.            cout << "\nYou can get the shape_predictor_68_face_landmarks.dat file from:\n"; 
69.            cout << "http://dlib.net/files/shape_predictor_68_face_landmarks.dat.bz2" << endl;//从这个地址下载模型标记点数据 
70.            return 0; 
71.        } 
72. 
73.        // We need a face detector.  We will use this to get bounding boxes for 
74.        // each face in an image. 
75.        //****需要一个人脸检测器,获得一个边界框 
76.        frontal_face_detector detector = get_frontal_face_detector(); 
77. 
78.        // And we also need a shape_predictor.  This is the tool that will predict face 
79.        // landmark positions given an image and face bounding box.  Here we are just 
80.        // loading the model from the shape_predictor_68_face_landmarks.dat file you gave 
81.        // as a command line argument. 
82.        //****也需要一个形状预测器,这是一个工具用来预测给定的图片和脸边界框的标记点的位置。 
83.        //****这里我们仅仅从shape_predictor_68_face_landmarks.dat文件加载模型 
84.        shape_predictor sp;//定义个shape_predictor类的实例 
85.        deserialize(argv[1]) >> sp; 
86. 
87. 
88.        image_window win, win_faces; 
89.        // Loop over all the images provided on the command line. 
90.        // ****循环所有图片 
91.        for (int i = 2; i < argc; ++i) 
92.        { 
93.            cout << "processing image " << argv[i] << endl; 
94.            array2d<rgb_pixel> img;//注意变量类型 rgb_pixel 三通道彩色图像 
95.            load_image(img, argv[i]); 
96.            // Make the image larger so we can detect small faces. 
97.            pyramid_up(img); 
98. 
99.            // Now tell the face detector to give us a list of bounding boxes 
100.            // around all the faces in the image. 
101.            std::vector<rectangle> dets = detector(img);//检测人脸,获得边界框 
102.            cout << "Number of faces detected: " << dets.size() << endl;//检测到人脸的数量 
103. 
104.            // Now we will go ask the shape_predictor to tell us the pose of 
105.            // each face we detected. 
106.            //****调用shape_predictor类函数,返回每张人脸的姿势 
107.            std::vector<full_object_detection> shapes;//注意形状变量的类型,full_object_detection 
108.            for (unsigned long j = 0; j < dets.size(); ++j) 
109.            { 
110.                full_object_detection shape = sp(img, dets[j]);//预测姿势,注意输入是两个,一个是图片,另一个是从该图片检测到的边界框 
111.                cout << "number of parts: " << shape.num_parts() << endl; 
112.                //cout << "pixel position of first part:  " << shape.part(0) << endl;//获得第一个点的坐标,注意第一个点是从0开始的 
113.                //cout << "pixel position of second part: " << shape.part(1) << endl;//获得第二个点的坐标 
114.                /*自己改写,打印出全部68个点*/ 
115.                for (int i = 1; i < 69; i++) 
116.                { 
117.                    cout << "第 " << i<< " 个点的坐标: " << shape.part(i-1) << endl; 
118.                } 
119.                // You get the idea, you can get all the face part locations if 
120.                // you want them.  Here we just store them in shapes so we can 
121.                // put them on the screen. 
122.                shapes.push_back(shape); 
123.            } 
124. 
125.            // Now let's view our face poses on the screen. 
126.            //**** 显示结果 
127.            win.clear_overlay(); 
128.            win.set_image(img); 
129.            win.add_overlay(render_face_detections(shapes)); 
130. 
131.            // We can also extract copies of each face that are cropped, rotated upright, 
132.            // and scaled to a standard size as shown here: 
133.            //****我们也能提取每张剪裁后的人脸的副本,旋转和缩放到一个标准尺寸 
134.            dlib::array<array2d<rgb_pixel> > face_chips; 
135.            extract_image_chips(img, get_face_chip_details(shapes), face_chips); 
136.            win_faces.set_image(tile_images(face_chips)); 
137. 
138.            cout << "Hit enter to process the next image..." << endl; 
139.            cin.get(); 
140.        } 
141.    } 
142.    catch (exception& e) 
143.    { 
144.        cout << "\nexception thrown!" << endl; 
145.        cout << e.what() << endl; 
146.    } 
147.} 
148. 
149.// ---------------------------------------------------------------------------------------- 


其他的和上一篇博客相同,祝大家好运!


   

CNN网络提取哪层输出作为最后提取的特征为宜?


在使用CNN提取特征时,到底使用哪一层的输出作为特征呢?很多人会说:“当然是最后一个全连接层了!,这有什么问题?”

    这还真有问题!我相信有很多人和我一样走入了一个误区,认为最后一个全连接层的输出连接最后的分类器,那么最后一个全连接层的输出当然是最后提取的特征了。知道昨天我读了一篇论文才恍然大悟,原来这样是错的!正确的答案是倒数第二个全连接层的输出才是最后要提取的特征。

   原因:最后一个全连接层的输出维度,在设计时是和训练样本的类别数一致的,比如你的训练要本有2622类,那么在设计最后的分类器时要有2622个输入,则最后一个全连接层的输出也是2622维的。这样最后一个全连接层的输出维度就和训练样本有了密切的关系,因此把它作为最后的特征显然不合适。

   注意:以上只是我的个人理解,如有不对之处,感谢指正!



  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值