You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

1:1 ROC与1:N ROC有什么区别?1:N人脸识别可用哪些评估指标?

1:N人脸识别评估相关问题解答

1:1 ROC与1:N ROC的核心差异

首先明确1:1人脸验证是二分类任务,对应ROC的计算逻辑是遍历相似度阈值,统计所有正样本对(同一人)、负样本对(不同人)在各阈值下的真阳性率(TPR,纵轴)和假阳性率(FPR,横轴)绘制曲线,结果和底库规模无关。
确实存在1:N ROC这类评估指标,它针对1:N人脸识别的检索匹配逻辑设计,和1:1 ROC的核心差异如下:

  • 匹配判定逻辑不同:1:N场景下每个待识别样本会输出和底库N个身份的相似度得分,判定正确的标准是「最高得分超过阈值,且对应身份为样本真实身份」,需同时考虑排序结果和阈值,和1:1仅判断单对样本是否匹配的逻辑完全不同
  • 关联底库规模:1:N ROC的表现直接和底库大小N强相关,N越大出现随机高分误匹配的概率越高,相同算法在N=100和N=10000的底库上得到的曲线差异极大,而1:1 ROC的表现不受底库规模影响
  • 指标定义不同:1:N ROC的横轴一般为误识率(FAR),指真实身份不在底库中的样本被错误判定为在库的比例;纵轴为识别率(TPR),指真实身份在底库中的样本被正确识别的比例,和1:1 ROC的横轴FPR(所有负样本对被误判为正的比例)定义完全不同

1:N人脸识别其他常用评估指标

除1:N ROC外,工业界和学术界常用的评估指标还有这些:

  • Top-k准确率:待识别样本的前k个匹配结果中包含真实身份的比例,常用Top-1、Top-5,仅评估排序效果,不涉及阈值判定
  • 漏识别率(FNMR):真实身份在底库中的样本未被正确识别的比例,和识别率为互补关系(FNMR = 1 - TPR)
  • 固定FAR下的识别率:实际部署最常用的指标,比如FAR=1e-6时的TPR,指控制误识率在百万分之一的安全标准下,算法能正确识别的样本比例
  • 库内拒识率:真实身份在底库中,但最高得分低于阈值被判定为不在库的比例

简易代码示例

以下是基于NumPy实现的1:N指标计算代码,可直接用于模拟或实际测试数据的指标统计:

import numpy as np

def calculate_1n_metrics(sim_scores: np.ndarray, query_labels: np.ndarray, gallery_labels: np.ndarray, thresholds: np.ndarray):
    """
    计算1:N人脸识别核心指标
    参数:
    sim_scores: 形状为(查询样本数, 底库样本数),值为查询样本与底库样本的相似度,越高越相似
    query_labels: 形状为(查询样本数,),每个查询样本的真实身份标签,-1代表真实身份不在底库中
    gallery_labels: 形状为(底库样本数,),底库中每个样本的身份标签
    thresholds: 待遍历的相似度阈值列表
    返回:
    far_list: 各阈值对应的误识率列表
    tpr_list: 各阈值对应的识别率列表
    top1_acc: Top1准确率
    """
    # 分离在库、不在库查询样本
    in_gallery_mask = query_labels != -1
    out_gallery_mask = query_labels == -1
    in_idx = np.where(in_gallery_mask)[0]
    out_idx = np.where(out_gallery_mask)[0]

    # 计算Top1准确率
    max_score_idx = np.argmax(sim_scores, axis=1)
    pred_labels = gallery_labels[max_score_idx]
    top1_acc = np.mean(pred_labels[in_idx] == query_labels[in_idx]) if len(in_idx) > 0 else 0.0

    far_list, tpr_list = [], []
    for th in thresholds:
        # 计算FAR:不在库样本的最高得分超过阈值的比例
        if len(out_idx) > 0:
            out_max_score = np.max(sim_scores[out_idx], axis=1)
            far = np.mean(out_max_score > th)
        else:
            far = 0.0
        far_list.append(far)

        # 计算TPR:在库样本最高得分超过阈值且预测正确的比例
        if len(in_idx) > 0:
            in_max_score = np.max(sim_scores[in_idx], axis=1)
            pred_correct = pred_labels[in_idx] == query_labels[in_idx]
            tpr = np.mean((in_max_score > th) & pred_correct)
        else:
            tpr = 0.0
        tpr_list.append(tpr)
    
    return far_list, tpr_list, top1_acc

# 测试示例
if __name__ == "__main__":
    # 模拟参数:1000个查询样本,1000个底库样本,20%查询样本不在底库中
    NUM_QUERY = 1000
    NUM_GALLERY = 1000
    # 生成模拟数据
    sim_scores = np.random.rand(NUM_QUERY, NUM_GALLERY)
    query_labels = np.random.randint(0, NUM_GALLERY, size=NUM_QUERY)
    query_labels[np.random.choice(NUM_QUERY, size=int(NUM_QUERY*0.2), replace=False)] = -1
    gallery_labels = np.arange(NUM_GALLERY)
    thresholds = np.arange(0.1, 1.0, 0.05)
    # 计算指标
    far_list, tpr_list, top1_acc = calculate_1n_metrics(sim_scores, query_labels, gallery_labels, thresholds)
    # 输出结果
    print(f"Top1准确率: {top1_acc:.4f}")
    print("阈值对应FAR/TPR:")
    for th, far, tpr in zip(thresholds, far_list, tpr_list):
        print(f"阈值{th:.2f} | FAR={far:.4f} | TPR={tpr:.4f}")

内容的提问来源于stack exchange,提问作者Ink

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.27 14:06:04