欢迎您访问 最编程 本站为您分享编程语言代码,编程技术文章!
您现在的位置是: 首页

采用百度人工智能开放平台完成人脸注册、识别和比对

最编程 2024-03-30 21:21:06
...

小知识,大挑战!本文正在参与“程序员必备小知识”创作活动。

本篇文章采用百度开发平台提供的AI接口,识别人脸、注册人脸,完成人脸对比。 软件采用QT设计,实时读取电脑摄像头的数据显示在画面上,点击按钮可以对当前摄像头画面的人脸进行注册、上传到服务器的人脸库,也可以对当前人脸进行对比,得到相识度。

一、百度人脸对比接口介绍

百度官网地址: ai.baidu.com/tech/face/c…

image.png

可以在线测试人脸对比效果:

image.png

image.png

识别率比较高:

image.png

采用在线API调用接口完成人脸对比相关操作是免费的,只是并发的次数有限制。并且也支持离线部署,使用起来比较灵活。

image.png

在下面页面可以开通服务: console.bce.baidu.com/ai/?_=15764…

image.png

人脸对比使用教程: cloud.baidu.com/doc/FACE/s/… 在这里官方提供了很详细的文档,主流语言都有SDK包下载,也有代码案例。

image.png

image.png

image.png

二、示例代码

2.1 UI界面采用QT开发

image.png

image.png

2.2 注册人脸核心代码

//注册人脸
void Widget::RegFace(const QImage image,QString group_id,QString user_id,QString user_info)
{

    QString requestUrl;
    QNetworkRequest request;

    //存放图片BASE64编码
    QString imgData;

    //打包请求参数赋值
    QJsonObject post_data;
    QJsonDocument document;

    //设置请求地址
    QUrl url;
    QByteArray post_param;

    //人脸注册的请求地址
    requestUrl = "https://aip.baidubce.com/rest/2.0/face/v3/faceset/user/add";

    //设置数据提交格式
    request.setHeader(QNetworkRequest::ContentTypeHeader, QVariant("application/json"));

    //将图片进行Base64编码
    imgData = QString(toBase64(image)); //编码后的图片大小不超过2M

    //设置请求参数: 通用的请求参数
    post_data.insert("image",imgData);

    //设置请求参数:
    post_data.insert("image_type","BASE64"); //(总数据大小应小于10M
    post_data.insert("group_id",group_id);  //组ID
    post_data.insert("user_id",user_id);    //用户ID
    post_data.insert("user_info",user_info); //用户信息

    //构造请求
    url.setUrl(requestUrl + "?access_token=" + ui->lineEdit_access_token->text());
    request.setUrl(url);

    document.setObject(post_data);
    post_param = document.toJson(QJsonDocument::Compact);

    //发送请求
    manager->post(request, post_param);
}

2.3 人脸搜索

//人脸搜索功能
void Widget::FindFace(const QImage image)
{
    QString requestUrl;
    QNetworkRequest request;

    //存放图片BASE64编码
    QString imgData;

    //打包请求参数赋值
    QJsonObject post_data;
    QJsonDocument document;

    //设置请求地址
    QUrl url;
    QByteArray post_param;

    //人脸搜索请求地址
    requestUrl = "https://aip.baidubce.com/rest/2.0/face/v3/search";

    //设置数据提交格式
    request.setHeader(QNetworkRequest::ContentTypeHeader, QVariant("application/json"));

    //将图片进行Base64编码
    imgData = QString(toBase64(image)); //编码后的图片大小不超过2M

    //设置请求参数: 通用的请求参数
    post_data.insert("image",imgData);

    //设置请求参数:
    post_data.insert("image_type","BASE64"); //(总数据大小应小于10M
    post_data.insert("group_id_list","wbyq1");  //组ID

    //构造请求
    url.setUrl(requestUrl + "?access_token=" + ui->lineEdit_access_token->text());
    request.setUrl(url);

    document.setObject(post_data);
    post_param = document.toJson(QJsonDocument::Compact);

    //发送请求
    manager->post(request, post_param);
}

2.4 base64编码

/*
将图片进行base64编码
*/
QByteArray Widget::toBase64(const QImage &image)
{
    //将要检测的图片进行BASE64编码
    QByteArray ba;
    QBuffer buffer(&ba);
    buffer.open(QIODevice::WriteOnly);
    //以png格式将图片数据写入ba
    image.save(&buffer,"jpg");

    buffer.close();
    return ba.toBase64();
}

2.5 反馈的结果解析

//解析反馈结果
void Widget::replyFinished(QNetworkReply *reply)
{
    displayInfo="";
    ui->label_state_display->setText("");

    int statusCode = reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt();

    //读取所有数据
    QByteArray replyData = reply->readAll();

    //判断状态码
    if(200 != statusCode)
    {
        //qDebug()<<"reply data is:"<<QString(replyData);
       // qDebug() << "Status code is error:" << statusCode;
        displayInfo=tr("解析错误,错误代码:%1,%2").arg(statusCode).arg(QString(replyData));
        ui->label_state_display->setText(displayInfo);
        return;
    }

    //qDebug()<<"reply data is:"<<QString(replyData);

    //人脸注册
    if(function_select==0)
    {
        //解析数据
        QJsonParseError json_error;
        QJsonDocument document = QJsonDocument::fromJson(replyData, &json_error);
        if(json_error.error == QJsonParseError::NoError)
        {
            //判断是否是对象,然后开始解析数据
            if(document.isObject())
            {
                QJsonObject obj = document.object();
                //解析错误代码
                if(obj.contains("error_code"))
                {
                    int error_code=obj.take("error_code").toInt();
                    switch (error_code) {
                    case 0: //成功
                        displayInfo="--人脸注册成功--";
                        break;
                    case 222202:
                        displayInfo="人脸注册错误:图片中没有检测到人脸";
                        break;
                    case 222210:
                        displayInfo="人脸库中用户下的人脸数目超过限制\n当前每个用户下限制人脸数目最大20张";
                        break;
                    case 110:
                    case 111:
                        displayInfo="token有效期为30天,注意需要定期更换.\n可联系软件作者.";
                        break;
                    default:
                        if(obj.contains("error_msg"))
                        {
                            displayInfo+=tr("人脸注册错误:%1\n").arg(error_code);
                            displayInfo+=obj.take("error_msg").toString();
                        }
                    }
                }
             }
         }
    }
    else if(function_select==1) //人脸搜索
    {
        //解析数据
        QJsonParseError json_error;
        QJsonDocument document = QJsonDocument::fromJson(replyData, &json_error);
        if(json_error.error == QJsonParseError::NoError)
        {
            //判断是否是对象,然后开始解析数据
            if(document.isObject())
            {
                QJsonObject obj = document.object();
                //解析错误代码
                if(obj.contains("error_code"))
                {
                    int error_code=obj.take("error_code").toInt();
                    switch (error_code) {
                    case 0: //成功
                        displayInfo="--人脸搜索成功--\n";
                        break;
                    case 222202:
                        displayInfo="人脸搜索错误:图片中没有检测到人脸";
                        break;
                    case 110:
                    case 111:
                        displayInfo="token密匙有效期为30天,注意需要定期更换.\n可联系软件作者.";
                        break;
                    default:
                        if(obj.contains("error_msg"))
                        {
                            displayInfo+=tr("人脸搜索错误:%1\n").arg(error_code);
                            displayInfo+=obj.take("error_msg").toString();
                        }
                    }

                    //人脸搜索成功
                    if(error_code==0)
                    {
                         if(obj.contains("result"))
                          {
                                QJsonObject obj1=obj.take("result").toObject();

                                //找到数组
                                QJsonArray faceArray = obj1.take("user_list").toArray();

                                for(int i = 0; i < faceArray.size(); i++)
                                {
                                    QJsonObject faceObj = faceArray.at(i).toObject();
                                    //相似度
                                    if(faceObj.contains("score"))
                                    {
                                         displayInfo+=tr("识别相似度:%1\n").arg(faceObj.take("score").toDouble());
                                    }

                                    //人脸分组ID
                                    if(faceObj.contains("group_id"))
                                    {
                                         displayInfo+=tr("人脸分组:%1\n").arg(faceObj.take("group_id").toString());
                                    }
                                    //用户ID
                                    if(faceObj.contains("user_id"))
                                    {
                                         displayInfo+=tr("电话号码:%1\n").arg(faceObj.take("user_id").toString());
                                    }
                                    //用户信息
                                    if(faceObj.contains("user_info"))
                                    {
                                         displayInfo+=tr("姓名:%1\n").arg(faceObj.take("user_info").toString());
                                    }

                                }
                          }
                    }
                }
             }
         }
    }
    ui->label_state_display->setText(displayInfo);
}