百度AI人脸检测与对比
1.注册账号
打开网站
https://ai.baidu.com/
,注册百度账号并登录
2.创建应用
3.技术文档
https://ai.baidu.com/ai-doc/FACE/yk37c1u4t
4.Spring Boot简单集成测试
pom.xml
配置:
<!--百度AI-->
<dependency>
<groupId>com.baidu.aip</groupId>
<artifactId>java-sdk</artifactId>
<version>4.9.0</version>
</dependency>
人脸识别
java
类
下面的
APPID/AK/SK
改成你的,找
2
张人像图片就可简单测试。
package com.hz.test;
import com.baidu.aip.face.AipFace;
import com.baidu.aip.face.MatchRequest;
import com.hz.utils.FileUtil;
import org.apache.tomcat.util.codec.binary.Base64;
import org.json.JSONObject;
import java.util.ArrayList;
import java.util.HashMap;
/**
* @Author: LNH
* @Date: 2024-11-12-21:27
* @Description:
*/
public class FaceTest {
// 设置APPID/AK/SK
private static String APP_ID = "116216384";
private static String API_KEY = "VYnavoYcxNRGnahgk50WaTSl";
private static String SECRET_KEY = "qHhZBJIZSDfcrn830R05BkPyHoRLSqZ9";
public static void main(String[] args) {
try {
// 初始化一个AipFace
AipFace client = new AipFace(APP_ID, API_KEY, SECRET_KEY);
// 可选:设置网络连接参数
client.setConnectionTimeoutInMillis(2000);
client.setSocketTimeoutInMillis(60000);
// 读本地图片
byte[] bytes =
FileUtil.readFileByBytes("C:\\Users\\Administrator\\Desktop\\a\\周杰伦1.jpg");
byte[] bytes2 =
FileUtil.readFileByBytes("C:\\Users\\Administrator\\Desktop\\a\\周杰伦1.jpg");
// 将字节转base64
String image1 = Base64.encodeBase64String(bytes);
String image2 = Base64.encodeBase64String(bytes2);
// 人脸对比
MatchRequest req1 = new MatchRequest(image1, "BASE64");
MatchRequest req2 = new MatchRequest(image2, "BASE64");
ArrayList<MatchRequest> requests = new ArrayList<>();
requests.add(req1);
requests.add(req2);
JSONObject res = client.match(requests);
System.out.println("人脸对比结果:");
System.out.println(res.toString(2));
//调用处理函数
handleMatchResult(res);
// 人脸检测
// 传入可选参数调用接口
HashMap<String, String> options = new HashMap<>();
options.put("face_field", "age");
options.put("max_face_num", "2");
options.put("face_type", "LIVE");
options.put("liveness_control", "LOW");
JSONObject res2 = client.detect(image1, "BASE64", options);
System.out.println("人脸检测信息:");
System.out.println(res2.toString(2));
//调用处理函数
handleDetectResult(res2);
} catch (Exception e) {
e.printStackTrace();
System.err.println("文件读取失败: " + e.getMessage());
}
}
private static void handleMatchResult(JSONObject result) {
int errorCode = result.getInt("error_code");
if (errorCode == 0) { // 成功的情况
double score = result.getJSONObject("result").getDouble("score");
String isSamePerson = score > 80 ? "==>可能是同一个人" : "==>不是同一个
人"; // 根据实际需求调整阈值
System.out.println("------人脸对比结果: ------\n" + isSamePerson + "\n
相似度:" + score + "\n");
} else {
System.out.println("人脸对比失败: " + result.getString("error_msg"));
}
}
private static void handleDetectResult(JSONObject result) {
int errorCode = result.getInt("error_code");
if (errorCode == 0) { // 成功的情况
int faceNum = result.getJSONObject("result").getInt("face_num");
if (faceNum > 0) {
JSONObject faceInfo =
result.getJSONObject("result").getJSONArray("face_list").getJSONObject(0);
int age = faceInfo.getInt("age");
System.out.println("\n------人脸检测结果: ------ \n检测到人脸,年龄约
为 " + age + " 岁");
} else {
System.out.println("人脸检测结果: 没有检测到人脸");
}
} else {
System.out.println("人脸检测失败: " + result.getString("error_msg"));
}
}
}
测试所需的工具类
package com.hz.utils;
import java.io.*;
/**
* @Author: LNH
* @Date: 2024-11-12-21:32
* @Description:
*/
/**
* 文件读取工具类
*/
public class FileUtil{
/**
* 读取文件内容,作为字符串返回
*/
public static String readFileAsString(String filePath) throws IOException {
File file = new File(filePath);
if (!file.exists()) {
throw new FileNotFoundException(filePath);
}
if (file.length() > 1024 * 1024 * 1024) {
throw new IOException("File is too large");
}
StringBuilder sb = new StringBuilder((int) (file.length()));
// 创建字节输入流
FileInputStream fis = new FileInputStream(filePath);
// 创建一个长度为10240的Buffer
byte[] bbuf = new byte[10240];
// 用于保存实际读取的字节数
int hasRead = 0;
while ( (hasRead = fis.read(bbuf)) > 0 ) {
sb.append(new String(bbuf, 0, hasRead));
}
fis.close();
return sb.toString();
}
/**
* 根据文件路径读取byte[] 数组
*/
public static byte[] readFileByBytes(String filePath) throws IOException {
File file = new File(filePath);
if (!file.exists()) {
throw new FileNotFoundException(filePath);
} else {
ByteArrayOutputStream bos = new ByteArrayOutputStream((int)
file.length());
BufferedInputStream in = null;
try {
in = new BufferedInputStream(new FileInputStream(file));
short bufSize = 1024;
byte[] buffer = new byte[bufSize];
int len1;
while (-1 != (len1 = in.read(buffer, 0, bufSize))) {
bos.write(buffer, 0, len1);
}
byte[] var7 = bos.toByteArray();
return var7;
} finally {
try {
if (in != null) {
in.close();
}
} catch (IOException var14) {
var14.printStackTrace();
}
bos.close();
}
}
}
}
人脸检测
相关请求参数、返回参数解释
百度官网解释很清楚
5.Spring Boot接口测试
改写成
Controller
接口,加入前端页面测试
FaceController.java
文件
package com.hz.controller;
import com.baidu.aip.face.AipFace;
import com.baidu.aip.face.MatchRequest;
import org.apache.tomcat.util.codec.binary.Base64;
import org.json.JSONObject;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;/**
* @Author: LNH
* @Date: 2024-11-13-9:45
* @Description:
*/
@RestController
public class FaceController {
// 设置APPID/AK/SK
private static final String APP_ID = "116216384";
private static final String API_KEY = "VYnavoYcxNRGnahgk50WaTSl";
private static final String SECRET_KEY = "qHhZBJIZSDfcrn830R05BkPyHoRLSqZ9";
//人脸对比
@PostMapping(value = "/match-faces", produces = "application/json")
public ResponseEntity<String> matchFaces(@RequestParam("image1")
MultipartFile image1,
@RequestParam("image2")
MultipartFile image2)
throws IOException {
// 初始化一个AipFace
AipFace client = new AipFace(APP_ID, API_KEY, SECRET_KEY);
// 读本地图片
byte[] bytes1 = image1.getBytes();
byte[] bytes2 = image2.getBytes();
// 将字节转base64
String imageStr1 = Base64.encodeBase64String(bytes1);
String imageStr2 = Base64.encodeBase64String(bytes2);
// 人脸对比
MatchRequest req1 = new MatchRequest(imageStr1, "BASE64");
MatchRequest req2 = new MatchRequest(imageStr2, "BASE64");
ArrayList<MatchRequest> requests = new ArrayList<>();
requests.add(req1);
requests.add(req2);
JSONObject res = client.match(requests);
JSONObject result = handleMatchResult(res);
// 返回 JSON 字符串
return ResponseEntity.ok(result.toString());
}
//人脸检测
@PostMapping("/detect-face")
public ResponseEntity<String> detectFace(@RequestParam("image")
MultipartFile image)
throws
IOException {
// 初始化一个AipFace
AipFace client = new AipFace(APP_ID, API_KEY, SECRET_KEY);
// 读本地图片
byte[] bytes = image.getBytes();
// 将字节转base64
String imageStr = Base64.encodeBase64String(bytes);
// 人脸检测
// 传入可选参数调用接口
HashMap<String, String> options = new HashMap<>();
options.put("face_field", "age");
options.put("max_face_num", "2");
options.put("face_type", "LIVE");
options.put("liveness_control", "LOW");
JSONObject res = client.detect(imageStr, "BASE64", options);
JSONObject result = handleDetectResult(res);
// 返回 JSON 字符串
return ResponseEntity.ok(result.toString());
}
//对比判断是否为同一个人
private JSONObject handleMatchResult(JSONObject result) {
int errorCode = result.getInt("error_code");
if (errorCode == 0) { // 成功的情况
double score = result.getJSONObject("result").getDouble("score");
String isSamePerson = score > 80 ? "可能是同一个人" : "不是同一个人"; //
根据实际需求调整阈值
result.put("isSamePerson", isSamePerson);
result.put("score", score);
} else {
result.put("error_msg", "人脸对比失败: " +
result.getString("error_msg"));
}
return result;
}
//人脸检测信息
private JSONObject handleDetectResult(JSONObject result) {
int errorCode = result.getInt("error_code");
if (errorCode == 0) { // 成功的情况
int faceNum = result.getJSONObject("result").getInt("face_num");
if (faceNum > 0) {
JSONObject faceInfo =
result.getJSONObject("result").getJSONArray("face_list").getJSONObject(0);
int age = faceInfo.getInt("age");
} else {
result.put("error_msg", "人脸检测结果: 没有检测到人脸");
}
} else {
result.put("error_msg", "人脸检测失败: " +
result.getString("error_msg"));
}
return result;
}
}
result.put("age", age);
index.html
文件
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>人脸对比与检测</title>
<style>
body {
font-family: Arial, sans-serif;
background-color: #f4f4f4;
margin: 0;
padding: 0;
}
h1 {
text-align: center;
color: #333;
}
form {
max-width: 600px;
margin: 20px auto;
padding: 20px;
background-color: #fff;
border-radius: 8px;
box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
}
input[type="file"] {
display: block;
margin-bottom: 10px;
}
button {
display: block;
width: 100%;
padding: 10px;
background-color: #007bff;
color: #fff;
border: none;
border-radius: 4px;
cursor: pointer;
font-size: 16px;
}
button:hover {
background-color: #0056b3;
}
#matchResult, #detectResult {
margin: 20px auto;
padding: 20px;
background-color: #fff;
border-radius: 8px;
box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
text-align: center;
font-size: 18px;
color: #333;
}
#matchResult p, #detectResult p {
margin: 0;
}
.success {
color: green;
}
.error {
color: red;
}
</style>
</head>
<body>
<h1>人脸对比与检测</h1>
<!-- 人脸对比表单 -->
<h2>人脸对比</h2>
<form id="matchForm">
<input type="file" name="image1" accept="image/*" required>
<input type="file" name="image2" accept="image/*" required>
<button type="submit">对比</button>
</form>
<div id="matchResult"></div>
<!-- 人脸检测表单 -->
<h2>人脸检测</h2>
<form id="detectForm">
<input type="file" name="image" accept="image/*" required>
<button type="submit">检测</button>
</form>
<div id="detectResult"></div>
<script src="https://code.jquery.com/jquery-3.7.1.min.js"></script>
<script>
$(document).ready(function() {
$('#matchForm').on('submit', function(event) {
event.preventDefault();
var formData = new FormData(this);
$.ajax({
url: '/match-faces',
type: 'POST',
data: formData,
contentType: false,
processData: false,
headers: {
'Accept': 'application/json'
},
success: function(response) {
console.log("Match response:", response);
if (response.isSamePerson && response.score !== undefined) {
$('#matchResult').html('<p class="success">人脸对比结果: '
+ response.isSamePerson + ' (相似度:' + response.score + ')</p>');
} else {
$('#matchResult').html('<p class="error">人脸对比失败: ' +
response.error_msg + '</p>');
}
},
error: function(error) {
console.error("Match error:", error);
$('#matchResult').html('<p class="error">人脸对比失败: ' +
error.responseJSON.error_msg + '</p>');
}
});
});
$('#detectForm').on('submit', function(event) {
event.preventDefault();
var formData = new FormData(this);
$.ajax({
url: '/detect-face',
type: 'POST',
data: formData,
contentType: false,
processData: false,
headers: {
'Accept': 'application/json'
},
success: function(response) {
console.log("Detect response:", response);
if (response.age !== undefined) {
$('#detectResult').html('<p class="success">人脸检测结果:
检测到人脸,年龄约为 ' + response.age + ' 岁</p>');
} else {
$('#detectResult').html('<p class="error">人脸检测结果: ' +
response.error_msg + '</p>');
}
},
error: function(error) {
console.error("Detect error:", error);
$('#detectResult').html('<p class="error">人脸检测失败: ' +
error.responseJSON.error_msg + '</p>');
}
});
});
});
</script>
</body>
</html>