登录后签到
切换到窄版
春风AI技术论坛
登录
立即注册
收藏本站
发布
门户
Portal
论坛
BBS
每日签到
签到领积分
春风AI技术论坛
»
论坛
›
AI科学与技术
›
AI实验室
›
ArcFace 相似度阈值别再抄 0.8 了
返回列表
发新帖
ArcFace 相似度阈值别再抄 0.8 了
[复制链接]
查看:
48
|
回复:
0
发表于 2026-10-20 18:58:19
|
显示全部楼层
|
阅读模式
一、出事:审计上线,查出 0 个重复
我在做一个学生刷脸考勤系统,其中一个功能是
脸库审计
:定期检查库里有没有「同一个人被录成了多个学号」。
实现思路很常规:把所有 512 维人脸特征取出来,两两算相似度,跨学号却相似度很高的,就判定为重复注册。
阈值我按网上常见资料写的是
0.8
。代码跑通了,接口返回 200,duplicate_pairs: 0 —— 看起来一切正常。
问题在于:我提前往库里塞了 3 张同一个人的照片,分别挂在 3 个不同学号下。
也就是说,正确答案应该是「至少 3 对重复」,而它告诉我 0 对。
更隐蔽的是:
它不报错。
接口正常、流程正常、日志正常,只是永远查不出东西。这种"静默失效"是最难发现的 bug。
二、排查:别猜,把分布打出来
我没有继续调参试运气,而是加了一个接口,把库里所有向量两两算一遍余弦相似度,直接把结果打印出来看:
结果(我真实库里的数字):
关系实测余弦相似度
同一个人的不同照片
0.547 / 0.559 / 0.568
不同人
最高 0.207,多数在 0.0 上下
同一人最高才 0.568,而我设的门槛是 0.8。
这不是阈值调得"有点松",是门槛
根本不可能被触发
——永远返回 0 个。
三、为什么是 0.45~0.65,而不是 0.8+
三个原因,缺一不可:
1. 我用的是已经 L2 归一化过的特征
insightface 的 normed_embedding 是 512 维且
已经归一化
的向量。两个单位向量做点积,结果就是余弦相似度,取值区间是 [-1, 1]。在这种口径下,同一人的不同照片通常落在
0.45~0.65
。
2. 人脸不是指纹
同一个人的两张照片,会受光照、角度、表情、清晰度影响。余弦相似度本身就到不了 0.9 —— 那是"同一张图"才有的分数。
3. 0.8 这个数字来自别的口径
常见资料里的 0.8+,通常对应:
未归一化
的向量做内积(数值范围完全不同),或
用欧氏距离 / 其他度量,或
换了一个模型(不同模型的特征分布差异很大)
把 A 口径的阈值套到 B 口径上,就是这个 bug 的全部原因。
四、改法:把"标定"变成一个可复现的流程
我没有把 0.45 直接写死,而是做了两件事:
4.1 先给一个看分布的接口
任何人在自己的数据上,都能先看真实分布,再决定阈值。
4.2 阈值做成可调参数 + 明确写清口径
改完之后,那 3 张同人照片立刻被查出来了。
五、顺手做了个聚类:比两两比对更有说服力
两两比对只能告诉你"A 和 B 像",
层次聚类
能告诉你"这一撮人是同一个人"
为什么用层次聚类而不是 KMeans?
因为 KMeans 要你
先告诉它有几个簇
,而"库里到底有几个人"恰恰是未知数。层次聚类不需要预设 K,按距离阈值切就行。
用它可以识别三类异常:
同一学号内相似度 < 0.40 →
脏数据
(这张脸可能录错了人)
不同学号间相似度 > 0.50 →
疑似一人多号
某个簇里混进了多个学号 →
强证据的重复注册
六、怎么证明它真的有效:一次踩坑后的评测
"能查重"这种话谁都会说,所以我补了一个评测脚本。
第一次跑出来是「召回 100%,但有 4 个误报」——我没有改判定把它变绿,而是去查为什么。
结果发现问题出在我的
测试数据标错了
:合成组用了跟负样本
同一个人
的照片,审计把他们判为重复其实是
判对了
,却被我算成了误报。是 ground truth 错了,不是审计错了。
于是改成三条硬约束:
独立评测库
:用环境变量把数据库和向量库指到临时目录,不碰真实数据,也不和后端抢 Milvus Lite 的单进程文件锁
身份唯一
:先用特征把素材聚成身份(>0.45 视为同一人),强制「一个身份只进一个组」
负样本独立性校验
:入库前验证两两相似度 < 0.40,确认彼此真的不是同一个人
最终结果:
指标结果
构造异常组4(1 组真实同人照片 + 3 组翻转/提亮增广)
命中4
召回率
100%
误报的跨组配对0
负样本3 个,被误报 0 个
规模限制必须说清楚
:我手上能检出人脸的素材只有 9 张,这是
小样本的正确性验证
,不是大规模基准测试。
七、三条能带走的经验
任何阈值都是「模型 + 度量 + 预处理」三者的函数
,换任何一个都要重新标定。看到别人写 0.8,先问一句:他的向量归一化了吗?用的什么距离?
先打分布,再定阈值。
加一个能打印相似度矩阵的接口,比你在那儿试 0.6 / 0.7 / 0.8 有效一百倍。
"不报错但结果不对"的 bug 最危险。
静默失效不会报警,唯一的防线是
构造你已知答案的测试数据
。
admin
admin
当前离线
积分
235
21
主题
0
回帖
235
积分
管理员
积分
235
发消息
回复
举报
版块导航
AI黑科速递
零基础学AI
AI实验室
AI趣味脑洞
AI行业观察
新手答疑专区
返回列表
发新帖
高级模式
B
Color
Image
Link
Quote
Code
Smilies
您需要登录后才可以回帖
登录
|
立即注册
本版积分规则
发表回复
回帖后跳转到最后一页
Archiver
手机版
小黑屋
Powered by
Discuz!
X5.0
© 2001-2026
Discuz! Team
.
春风AI技术论坛
在本版发帖
返回顶部
快速回复
返回顶部
返回列表