找回密码
 立即注册
收起左侧

opencv dlib库的问题

1
回复
94
查看
[复制链接]
累计签到:7 天
连续签到:1 天
来源: 2019-5-13 11:35:22 显示全部楼层 |阅读模式
1Qter豆
有人配置好了opencv的dlib库么?帮我运行一下这段代码,想看一下结果如何,我的dlib库配置没有成功,谢谢。图中的照片如下。
[pre]#include <dlib/opencv.h>  
#include <opencv2/opencv.hpp>  
#include <dlib/image_processing/frontal_face_detector.h>  
#include <dlib/image_processing/render_face_detections.h>  
#include <dlib/image_processing.h>  
#include <dlib/gui_widgets.h>  
#include <vector>
#include<math.h>

using namespace dlib;
using namespace std;

#define PI 3.1415926535

double Angle(cv::Point o, cv::Point s, cv::Point e)
{
        double cosfi = 0, fi = 0, norm = 0;
        double dsx = s.x - o.x;
        double dsy = s.y - o.y;
        double dex = e.x - o.x;
        double dey = e.y - o.y;

        cosfi = dsx * dex + dsy * dey;
        norm = (dsx * dsx + dsy * dsy) * (dex * dex + dey * dey);
        cosfi /= sqrt(norm);

        if (cosfi >= 1.0) return 0;
        if (cosfi <= -1.0) return PI;
        fi = acos(cosfi);

        if (180 * fi / PI < 180)
        {
                return 180 * fi / PI;
        }
        else
        {
                return 360 - 180 * fi / PI;
        }
}

void FittingCurve(std::vector<cv::Point> vec, double * index, int len)
{
        double *px = new double[vec.size()];
        double *py = new double[len*vec.size()];
        int i = 0;
        for (std::vector<cv::Point>::iterator itr = vec.begin(); itr != vec.end(); ++itr)
        {
                px[i] = (*itr).x;
                int j = 0;
                while (j<len)
                {
                        py[len*i + j] = pow((*itr).y, double(j));
                        j++;
                }
                i++;
        }

        CvMat xMat = cvMat(vec.size(), 1, CV_64FC1, px);
        CvMat yMat = cvMat(vec.size(), len, CV_64FC1, py);
        CvMat *yTransposedMat = cvCreateMat(yMat.cols, yMat.rows, CV_64FC1);
        cvTranspose(&yMat, yTransposedMat);//求yMat的转置

        double *a = new double[len*len];
        for (int i = 0; i<len*len; ++i)
        {
                a[i] = 0;
        }
        CvMat invMat1 = cvMat(len, len, CV_64FC1, a);
        cvGEMM(yTransposedMat, &yMat, 1, NULL, 0, &invMat1, 0);//yMat的转置与yMat矩阵相乘
        cvInvert(&invMat1, &invMat1, 0);//求invMat的逆矩阵

        double *b = new double[len];
        for (int i = 0; i<len; ++i)
        {
                b[i] = 0;
        }
        CvMat invMat2 = cvMat(len, 1, CV_64FC1, b);
        cvGEMM(yTransposedMat, &xMat, 1, NULL, 0, &invMat2, 0);//求yMat的转置矩阵与xMat矩阵相乘


        cvGEMM(yTransposedMat, &xMat, 1, NULL, 0, &invMat2, 0);//求yTransposedMat矩阵与xMat 矩阵的乘积
        CvMat indexMat = cvMat(len, 1, CV_64FC1, index);
        cvGEMM(&invMat1, &invMat2, 1, NULL, 0, &indexMat, 0);


        cvReleaseMat(&yTransposedMat);
        delete[] a;
        delete[] b;
        delete[] px;
        delete[] py;
}

bool polynomial_curve_fit(std::vector<cv::Point>& key_point, int n, cv::Mat& A)
{
        //Number of key points  
        int N = key_point.size();

        //构造矩阵X  
        cv::Mat X = cv::Mat::zeros(n + 1, n + 1, CV_64FC1);
        for (int i = 0; i < n + 1; i++)
        {
                for (int j = 0; j < n + 1; j++)
                {
                        for (int k = 0; k < N; k++)
                        {
                                X.at<double>(i, j) = X.at<double>(i, j) +
                                        std::pow(key_point[k].x, i + j);
                        }
                }
        }

        //构造矩阵Y  
        cv::Mat Y = cv::Mat::zeros(n + 1, 1, CV_64FC1);
        for (int i = 0; i < n + 1; i++)
        {
                for (int k = 0; k < N; k++)
                {
                        Y.at<double>(i, 0) = Y.at<double>(i, 0) +
                                std::pow(key_point[k].x, i) * key_point[k].y;
                }
        }

        A = cv::Mat::zeros(n + 1, 1, CV_64FC1);
        //求解矩阵A  
        cv::solve(X, Y, A, cv::DECOMP_LU);
        return true;
}

void facetype(full_object_detection face)
{
        //0-16
        int x[17], y[17];
        for (int i = 0, j = 0; i <= 16; i++, j++)
        {
                x[j] = face.part(i).x();
                y[j] = face.part(i).y();
        }
        double len = sqrt((x[0] - x[16])*(x[0] - x[16]));
        double high = sqrt((y[4] - y[8])*(y[4] - y[8]));
        double s_all = len*high;
        double a = sqrt((x[4] - x[8])*(x[4] - x[8]) + (y[4] - y[8])*(y[4] - y[8]));
        double b = sqrt((x[12] - x[8])*(x[12] - x[8]) + (y[12] - y[8])*(y[12] - y[8]));
        double c = sqrt((x[4] - x[12])*(x[4] - x[12]) + (y[4] - y[12])*(y[4] - y[12]));
        double q = (a + b + c) / 2;
        double s_part = sqrt(q*(q - a)*(q - b)*(q - c));
        double ratio = s_part / s_all;
        cout << "下巴比例:" << ratio << endl;
        if (ratio > 0.48)
                cout << "该目标下巴偏粗" << endl;
        else
                cout << "该目标下巴偏细" << endl;
        //cv::Mat image = cv::Mat::zeros(800, 700, CV_8UC3);
        //image.setTo(cv::Scalar(100, 0, 0));
        ////输入拟合点   
        //std::vector<cv::Point> points;
        //for (int i = 0; i < 17; i++)
        //{
        //        points.push_back(cv::Point(x[i], y[i]));
        //}

        ////将拟合点绘制到空白图上   
        //for (int i = 0; i < points.size(); i++)
        //{
        //        cv::circle(image, points[i], 5, cv::Scalar(0, 0, 255), 2, 8, 0);
        //}

        ////绘制折线  
        //cv::polylines(image, points, false, cv::Scalar(0, 255, 0), 1, 8, 0);

        //cv::Mat A;

        //polynomial_curve_fit(points, 3, A);
        //std::cout << "A(face) = " << A << std::endl;

        //std::vector<cv::Point> points_fitted;

        //for (int x = 0; x < 700; x++)
        //{
        //        /*double y = A.at<double>(0, 0) + A.at<double>(1, 0) * x +
        //        A.at<double>(2, 0)*std::pow(x, 2) + A.at<double>(3, 0)*std::pow(x, 3);*/
        //        double y = A.at<double>(0, 0) + A.at<double>(1, 0) * x +
        //                A.at<double>(2, 0)*std::pow(x, 2) + A.at<double>(3, 0)*std::pow(x, 3);

        //        points_fitted.push_back(cv::Point(x, y));
        //}
        //cv::polylines(image, points_fitted, false, cv::Scalar(0, 255, 255), 1, 8, 0);

        //cv::imshow("facetype", image);
}

void faceout(full_object_detection face)
{
        ofstream ofile;               //定义输出文件
        ofile.open("facedata.txt");     //作为输出文件打开
        for (int i = 0, j = 0; i <= 16; i++, j++)
                ofile << face.part(i).x() <<" "<< face.part(i).y()<<endl;
        ofile.close();
}

void facetype2(full_object_detection face)
{
        std::vector<cv::Point> vec;
        //0-16
        int x[17], y[17];
        for (int i = 0, j = 0; i <= 16; i++, j++)
        {
                x[j] = face.part(i).x();
                y[j] = face.part(i).y();
        }
        cv::Mat image = cv::Mat::zeros(800, 700, CV_8UC3);
        image.setTo(cv::Scalar(100, 0, 0));
        //输入拟合点   
        for (int i = 0; i < 17; i++)
        {
                vec.push_back(cv::Point(x[i], y[i]));
        }

        //将拟合点绘制到空白图上   
        for (int i = 0; i < vec.size(); i++)
        {
                cv::circle(image, vec[i], 5, cv::Scalar(0, 0, 255), 2, 8, 0);
        }

        //绘制折线  
        cv::polylines(image, vec, false, cv::Scalar(0, 255, 0), 1, 8, 0);

        double index[3];
        FittingCurve(vec, index, 3);
        std::cout << "A(face) = " << index[0] << ";" << endl << index[1] << ";" <<endl << index[2] << ";" << endl;

        std::vector<cv::Point> points_fitted;

        for (int x = 0; x < 700; x++)
        {
                /*double y = A.at<double>(0, 0) + A.at<double>(1, 0) * x +
                A.at<double>(2, 0)*std::pow(x, 2) + A.at<double>(3, 0)*std::pow(x, 3);*/
                double y = index[0] + index[1] * x +index[2]*std::pow(x, 2);

                points_fitted.push_back(cv::Point(x, y));
        }
        cv::polylines(image, points_fitted, false, cv::Scalar(0, 255, 255), 1, 8, 0);

        cv::imshow("facetype", image);
}

void nosetype(full_object_detection face)
{
        //27-35
        double a = sqrt((face.part(27).x() - face.part(31).x())*(face.part(27).x() - face.part(31).x()) +
                (face.part(27).y() - face.part(31).y())*(face.part(27).y() - face.part(31).y()));
        double b = sqrt((face.part(27).x() - face.part(35).x())*(face.part(27).x() - face.part(35).x()) +
                (face.part(27).y() - face.part(35).y())*(face.part(27).y() - face.part(35).y()));
        double c = sqrt((face.part(35).x() - face.part(31).x())*(face.part(35).x() - face.part(31).x()) +
                (face.part(35).y() - face.part(31).y())*(face.part(35).y() - face.part(31).y()));
        double p = (a + b + c) / 2;
        double len = sqrt((face.part(1).x() - face.part(15).x())*(face.part(1).x() - face.part(15).x()) +
                (face.part(1).y() - face.part(15).y())*(face.part(1).y() - face.part(15).y()));
        double wid1 = sqrt((face.part(0).x() - face.part(2).x())*(face.part(0).x() - face.part(2).x()) +
                (face.part(0).y() - face.part(2).y())*(face.part(0).y() - face.part(2).y()));
        double wid2 = sqrt((face.part(14).x() - face.part(16).x())*(face.part(14).x() - face.part(16).x()) +
                (face.part(14).y() - face.part(16).y())*(face.part(14).y() - face.part(16).y()));
        double wid = (wid1 + wid2) / 2;
        double s_nose = sqrt(p*(p - a)*(p - b)*(p - c));
        double s_face = len*wid;
        double ratio = s_nose / s_face;
        cout << "目标鼻子比例为:" << ratio << endl;
        if (ratio > 0.13)
                cout << "该目标为大鼻子" << endl;
        else
                cout << "该目标为小鼻子" << endl;

}

void eyetype(full_object_detection face,double *k)
{
        int x[4], y[4];
        for (int i = 36, j = 0; i <= 39; i++, j++)
        {
                x[j] = face.part(i).x();
                y[j] = face.part(i).y();
        }

        /*for (int i = 0; i < 4; i++)
        {
                vec.push_back(cvPoint2D64f(x[i], y[i]));
        }
        double index[3];
        FittingCurve(vec, index, 3);
        for (int i = 0; i < 3; ++i)
        {
                cout << index[i] << endl;
        }*/
        cv::Mat image = cv::Mat::zeros(480, 640, CV_8UC3);
        image.setTo(cv::Scalar(100, 0, 0));

        //输入拟合点   
        std::vector<cv::Point> points;
        for (int i = 0; i < 4; i++)
        {
                points.push_back(cv::Point(x[i], y[i]));
        }

        //将拟合点绘制到空白图上   
        for (int i = 0; i < points.size(); i++)
        {
                cv::circle(image, points[i], 5, cv::Scalar(0, 0, 255), 2, 8, 0);
        }

        //绘制折线  
        cv::polylines(image, points, false, cv::Scalar(0, 255, 0), 1, 8, 0);

        cv::Mat A;

        polynomial_curve_fit(points, 2, A);
        std::cout << "A(eye) = " << A << std::endl;

        std::vector<cv::Point> points_fitted;

        for (int x = 0; x < 400; x++)
        {
                /*double y = A.at<double>(0, 0) + A.at<double>(1, 0) * x +
                        A.at<double>(2, 0)*std::pow(x, 2) + A.at<double>(3, 0)*std::pow(x, 3);*/
                double y = A.at<double>(0, 0) + A.at<double>(1, 0) * x +
                        A.at<double>(2, 0)*std::pow(x, 2);

                points_fitted.push_back(cv::Point(x, y));
        }

        for (int i = 0; i < 4; i++)
        {
                k[i] = A.at<double>(1, 0) + A.at<double>(2, 0)*points[i].x;
        }

        cv::polylines(image, points_fitted, false, cv::Scalar(0, 255, 255), 1, 8, 0);

        cv::imshow("eyetype", image);
}

double eyecal(double *k1,double *k2)
{
        double addson = 0;
        double addmo1 = 0;
        double addmo2 = 0;
        for (int i = 0; i < 4; i++)
        {
                addson += k1[i] * k2[i];
                addmo1 += k1[i] * k1[i];
                addmo2 += k2[i] * k2[i];
        }
        double addmo = sqrt(addmo1*addmo2);
        double similarity = addson / addmo;
        return similarity;
}

void eyejudge(full_object_detection face1, full_object_detection face2, full_object_detection face3)
{
        double k0[4];
        double k1[4];
        double k2[4];
        eyetype(face1, k0);
        eyetype(face2, k1);
        eyetype(face3, k2);
        double sim1 = eyecal(k0, k1);
        double sim2 = eyecal(k0, k2);
        cout << "与大眼睛样本相似度为:" << sim1 << endl;
        cout << "与小眼睛样本相似度为:" << sim2 << endl;
        if (sim1 > sim2)
        {
                cout << "该目标眼睛偏大" << endl;
        }
        else
        {
                cout << "该目标眼睛偏小" << endl;
        }
}

void mousetype(full_object_detection face)
{
        double b = sqrt((face.part(66).x() - face.part(57).x())*(face.part(66).x() - face.part(57).x()) +
                (face.part(66).y() - face.part(57).y())*(face.part(66).y() - face.part(57).y()));
        double a = sqrt((face.part(48).x() - face.part(54).x())*(face.part(48).x() - face.part(54).x()) +
                (face.part(48).y() - face.part(54).y())*(face.part(48).y() - face.part(54).y())) / 2;
        double c = sqrt(a*a - b*b);
        double e = c / a;
        cout <<"目标嘴唇离心率为:" << e << endl;
        if (e > 0.85)
                cout << "该目标为薄嘴唇" << endl;
        else
                cout << "该目标为厚嘴唇" << endl;
}

int main()
{
        clock_t start, end;
        start = clock();
        frontal_face_detector detector = get_frontal_face_detector();
        shape_predictor pose_model;
        deserialize("shape_predictor_68_face_landmarks.dat") >> pose_model;

        // Grab and process frames until the main window is closed by the user.  
        // Grab a frame  
        cv::Mat temp = cv::imread("mat3.jpg");
        /*cv::Mat tempbig = cv::imread("bigeye.jpg");
        cv::Mat tempsmall = cv::imread("smalleye.jpg");*/

        cv_image<bgr_pixel> cimg(temp);
        /*cv_image<bgr_pixel> cimgbig(tempbig);
        cv_image<bgr_pixel> cimgsmall(tempsmall);*/
        // Detect faces   
        std::vector<rectangle> faces = detector(cimg);
        /*std::vector<rectangle> facesbig = detector(cimgbig);
        std::vector<rectangle> facessmall = detector(cimgsmall);*/
        // Find the pose of each face.  
        std::vector<full_object_detection> shapes;
        /*std::vector<full_object_detection> shapesbig;
        std::vector<full_object_detection> shapessmall;*/
        int num_per;
        for (unsigned long i = 0; i < faces.size(); ++i)
        {
                shapes.push_back(pose_model(cimg, faces[i]));
                num_per = i + 1;
        }

        /*int num_perbig;
        for (unsigned long i = 0; i < facesbig.size(); ++i)
        {
                shapesbig.push_back(pose_model(cimgbig, facesbig[i]));
                num_perbig = i + 1;
        }

        int num_persmall;
        for (unsigned long i = 0; i < facessmall.size(); ++i)
        {
                shapessmall.push_back(pose_model(cimgsmall, facessmall[i]));
                num_persmall = i + 1;
        }

        std::vector<full_object_detection> bigeye;
        std::vector<full_object_detection> smalleye;*/


        for (int i = 0; i < num_per;i++)
        {
                for (int j = 0; j < 68; j++)
                {
                        circle(temp, cvPoint(shapes[i].part(j).x(), shapes[i].part(j).y()), 3, cv::Scalar(0, 0, 255), -1);
                        //  shapes[0].part(i).x();//68个  
                        putText(temp, to_string(j), cvPoint(shapes[i].part(j).x(), shapes[i].part(j).y()), CV_FONT_HERSHEY_PLAIN, 1, cv::Scalar(255, 0, 0), 1, 4);
                }
                /*nosetype(shapes[i]);
                mousetype(shapes[i]);
                eyetype(shapes[i]);
                faceout(shapes[i]);*/
                /*eyejudge(shapes[i], shapesbig[0], shapessmall[0]);*/
                facetype(shapes[i]);
                nosetype(shapes[i]);
                mousetype(shapes[i]);
        }

        imshow("Dlib特征点", temp);
        cv::waitKey(0);
}

回复

使用道具 举报

累计签到:7 天
连续签到:1 天
2019-5-13 11:37:01 显示全部楼层
图片太大了不能上传,大佬可以加下我QQ 654265613
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册