本节通过翔云OCR云平台来实现人脸识别。调用人脸对比API,通过https post方式向云服务器提交两张需要对比的图片Base64流以及其他信息,云服务器处理后返回判断结果。
翔云OCR云平台:https://www.netocr.com/
上一节安装了libcurl库,有以下步骤:
1、./configure --prefix=$PWD/_install 配置安装路径为当前路径下_install文件夹
2、make 编译
3、make install 编译后的文件拷贝到指定文件夹,此时才会出现_install文件夹
我们会发现程序使用https协议不能连通,因为https=http+ssl,还需要安装并使用ssl相关库,可以查看下curl-7.71.1/docs/INSTALL.md,有以下说明:
The configure script always tries to find a working SSL library unless
explicitly told not to. If you have OpenSSL installed in the default search
path for your compiler/linker, you don’t need to do anything special. If you
have OpenSSL installed in/usr/local/ssl
, you can run configure like:./configure --with-ssl
If you have OpenSSL installed somewhere else (for example,
/opt/OpenSSL
) and
you have pkg-config installed, set the pkg-config path first, like this:env PKG_CONFIG_PATH=/opt/OpenSSL/lib/pkgconfig ./configure --with-ssl
Without pkg-config installed, use this:
./configure --with-ssl=/opt/OpenSSL
我们需要安装下OpenSSL库,./configure --with-ssl默认从/usr/local/路径找OpenSSL库并调用。
1、先移除_install文件夹(之前libcurl安装的路径)
rm _install -rf
2、从网络上自动下载openssl-1.1.1a.tar.gz
wget https://www.openssl.org/source/openssl-1.1.1a.tar.gz
3、解压openssl-1.1.1a.tar.gz
tar -xvf opemssl-1.1.1a.tar.gz
4、浏览/openssl-1.1.1a/INSTALL文件,查看安装步骤说明:
If you want to just get on with it, do:
on Unix (again, this includes Mac OS/X):
$ ./config
$ make
$ make install
This will build and install OpenSSL in the default location, which is: Unix: normal installation directories under
/usr/local
5、Openssl库安装步骤:
(1)./config
(2)make
(3)sudo make install(安装在usr/local,需要root模式)
6、Openssl库安装完成后,进入curl-7.71.1文件夹,通过./configure配置
./configure --prefix=$PWD/_install --with-ssl
后面的步骤一样:
make 编译
make install 编译后的文件拷贝到指定文件夹,此时才会出现_install文件夹
libcurl库安装完成
用户ocrKey和ocrSecret在个人中心页面可以看到。
注意的是,img1和img2是图片base64流,base64流简单来说就是将图片二进制数据通过Base64编码成字符串类型数据。
1、url设置
curl_easy_setopt(curl, CURLOPT_URL, “https://netocr.com/api/faceliu.do”);
2、提交参数的设置
提交参数格式:&attr1=value1&attr2=value2…
sprintf(PostString,"&img1=%s&img2=%s&key=%s&secret=%s&typeId=%d&format=%s",img1,img2,key,secret,typeId,format);
curl_easy_setopt(curl, CURLOPT_POSTFIELDS,PostString);
3、返回的数据(xml格式)
<?xml version="1.0" encoding="UTF-8"?>
<data>
<message>
<status>0</status>
<value>比对完成</value>
</message>
<cardsinfo>
<card type="21">
<item desc="判定值"><![CDATA[0.9075357]]></item> //对比率为0.9075357
<item desc="判定结果"><![CDATA[是]]></item> //判断为是同一个人
</card>
</cardsinfo>
</data>
shell指令补充
将图片数据进行base64编码,得到图片base64流
base64 xxx (xxx为图片文件,可以为png、jpg等格式)
#include
#include
#include
#include
#include
#include
#include
#include
#define true 1
#define false 0
typedef unsigned int bool;
char post_info[500];
size_t ReadHandler( void *ptr, size_t size, size_t nmemb, void *stream)
{
int buf_size=size*nmemb;
char *buf=malloc(buf_size+1);
memset(buf,'\0',buf_size+1);
strncpy(buf,ptr,buf_size);
printf("%s\n",buf);
strcat(post_info,buf);
free(buf);
return buf_size;
}
char* getBase64(char *img_name)
{
int fd;
int size=0;
char cmd[30];
char *img_buf;
sprintf(cmd,"base64 %s >tmpfile.txt",img_name);
if(system(cmd)==256)
{
return NULL;
}
fd=open("tmpfile.txt",O_RDWR);
size=lseek(fd,0,SEEK_END);
img_buf=malloc(size+2);
memset(img_buf,'\0',size+2);
lseek(fd,0,SEEK_SET);
read(fd,img_buf,size);
close(fd);
system("rm tmpfile.txt");
return img_buf;
}
bool postUrl(char* img1_name,char* img2_name)
{
CURL *curl;
CURLcode res;
char *PostString;
char *img1;
char *img2;
char *key="yourkey";
char *secret="yoursecret";
int typeId=21;
char *format="xml";
img1=getBase64(img1_name);
img2=getBase64(img2_name);
if((img1==NULL)||(img2==NULL))
{
printf("img dont exist!\n");
return false;
}
PostString=malloc(strlen(img1)+strlen(img2)+strlen(key)+strlen(secret)+sizeof(typeId)+strlen(format));
sprintf(PostString,"&img1=%s&img2=%s&key=%s&secret=%s&typeId=%d&format=%s",img1,img2,key,secret,typeId,format);
curl = curl_easy_init();
if (curl)
{
curl_easy_setopt(curl, CURLOPT_URL, "https://netocr.com/api/faceliu.do");
curl_easy_setopt(curl, CURLOPT_POSTFIELDS,PostString);
curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, ReadHandler);
res = curl_easy_perform(curl);
printf("OK:%d\n",res);
curl_easy_cleanup(curl);
if(strstr(post_info,"是")!=NULL)
{
printf("same person\n");
}
else
{
printf("different person\n");
}
}
return true;
}
int main(int argc,char* argv[])
{
memset(post_info,'\0',500);
if(argc!=3)
{
return -1;
}
curl_global_init(CURL_GLOBAL_ALL);
postUrl(argv[1],argv[2]);
curl_global_cleanup();
}
通过运行如下命令,来进行人脸对比,img1和img2代表两张要对比的图片。
./mycurl img1 img2
准备图片文件
从左到右文件名依次是reba1.png、reba2.png、xiang1.png。
运行结果
sh@ubuntu:~/Desktop/mycurl/test$ export LD_LIBRARY_PATH="/home/sh/Desktop/mycurl/curl-7.71.1/_install/lib"
sh@ubuntu:~/Desktop/mycurl/test$ gcc demo3.c -I /home/sh/Desktop/mycurl/curl-7.71.1/_install/include -lcurl -L /home/sh/Desktop/mycurl/curl-7.71.1/_install/lib -o mycurl
sh@ubuntu:~/Desktop/mycurl/test$ ./mycurl reba1.png reba2.png
"1.0" encoding="UTF-8"?>
<data>
0</status>
比对完成</value>
</message>
type="21">
- "判定值"><![CDATA[0.9565811]]></item>
- "判定结果"><![CDATA[是]]></item>
</card>
</cardsinfo>
</data>
OK:0
same person
sh@ubuntu:~/Desktop/mycurl/test$ ./mycurl reba1.png xiang1.png
"1.0" encoding="UTF-8"?>
<data>
0</status>
比对完成</value>
</message>
type="21">
- "判定值"><![CDATA[0.5085605]]></item>
- "判定结果"><![CDATA[否]]></item>
</card>
</cardsinfo>
</data>
OK:0
different person
本节仅仅是两张已准备好的图片进行对比,下节采用摄像头采集图片的方式进行人脸识别。