mirror of https://github.com/open-mmlab/mmocr.git
199 lines
12 KiB
Markdown
199 lines
12 KiB
Markdown
# 模型评测
|
||
|
||
```{note}
|
||
阅读此文档前,建议您先了解 {external+mmengine:doc}`MMEngine: 模型精度评测基本概念 <tutorials/evaluation>`。
|
||
```
|
||
|
||
## 评测指标
|
||
|
||
MMOCR 基于 {external+mmengine:doc}`MMEngine: BaseMetric <design/evaluation>` 基类实现了常用的文本检测、文本识别以及关键信息抽取任务的评测指标,用户可以通过修改配置文件中的 `val_evaluator` 与 `test_evaluator` 字段来便捷地指定验证与测试阶段采用的评测方法。例如,以下配置展示了如何在文本检测算法中使用 `HmeanIOUMetric` 来评测模型性能。
|
||
|
||
```python
|
||
# 文本检测任务中通常使用 HmeanIOUMetric 来评测模型性能
|
||
val_evaluator = [dict(type='HmeanIOUMetric')]
|
||
|
||
# 此外,MMOCR 也支持相同任务下的多种指标组合评测,如同时使用 WordMetric 及 CharMetric
|
||
val_evaluator = [
|
||
dict(type='WordMetric', mode=['exact', 'ignore_case', 'ignore_case_symbol']),
|
||
dict(type='CharMetric')
|
||
]
|
||
```
|
||
|
||
```{tip}
|
||
更多评测相关配置请参考[评测配置教程](../user_guides/config.md#评测配置)。
|
||
```
|
||
|
||
如下表所示,MMOCR 目前针对文本检测、识别、及关键信息抽取等任务共内置了 5 种评测指标,分别为 `HmeanIOUMetric`,`WordMetric`,`CharMetric`,`OneMinusNEDMetric`,和 `F1Metric`。
|
||
|
||
| | | | |
|
||
| --------------------------------------- | ------------ | ------------------------------------------------- | --------------------------------------------------------------------- |
|
||
| 评测指标 | 任务类型 | 输入字段 | 输出字段 |
|
||
| [HmeanIOUMetric](#hmeanioumetric) | 文本检测 | `pred_polygons`<br>`pred_scores`<br>`gt_polygons` | `recall`<br>`precision`<br>`hmean` |
|
||
| [WordMetric](#wordmetric) | 文本识别 | `pred_text`<br>`gt_text` | `word_acc`<br>`word_acc_ignore_case`<br>`word_acc_ignore_case_symbol` |
|
||
| [CharMetric](#charmetric) | 文本识别 | `pred_text`<br>`gt_text` | `char_recall`<br>`char_precision` |
|
||
| [OneMinusNEDMetric](#oneminusnedmetric) | 文本识别 | `pred_text`<br>`gt_text` | `1-N.E.D` |
|
||
| [F1Metric](#f1metric) | 关键信息抽取 | `pred_labels`<br>`gt_labels` | `macro_f1`<br>`micro_f1` |
|
||
|
||
通常来说,每一类任务所采用的评测标准是约定俗成的,用户一般无须深入了解或手动修改评测方法的内部实现。然而,为了方便用户实现更加定制化的需求,本文档将进一步介绍了 MMOCR 内置评测算法的具体实现策略,以及可配置参数。
|
||
|
||
### HmeanIOUMetric
|
||
|
||
[HmeanIOUMetric](mmocr.evaluation.metrics.hmean_iou_metric.HmeanIOUMetric) 是文本检测任务中应用最广泛的评测指标之一,因其计算了检测精度(Precision)与召回率(Recall)之间的调和平均数(Harmonic mean, H-mean),故得名 `HmeanIOUMetric`。记精度为 *P*,召回率为 *R*,则 `HmeanIOUMetric` 可由下式计算得到:
|
||
|
||
```{math}
|
||
H = \frac{2}{\frac{1}{P} + \frac{1}{R}} = \frac{2PR}{P+R}
|
||
```
|
||
|
||
另外,由于其等价于 {math}`\beta = 1` 时的 F-score (又称 F-measure 或 F-metric),`HmeanIOUMetric` 有时也被写作 `F1Metric` 或 `f1-score` 等:
|
||
|
||
```{math}
|
||
F_1=(1+\beta^2)\cdot\frac{PR}{\beta^2\cdot P+R} = \frac{2PR}{P+R}
|
||
```
|
||
|
||
在 MMOCR 的设计中,`HmeanIOUMetric` 的计算可以概括为以下几个步骤:
|
||
|
||
1. 过滤无效的预测边界盒
|
||
|
||
- 依据置信度阈值 `pred_score_thrs` 过滤掉得分较低的预测边界盒
|
||
- 依据 `ignore_precision_thr` 阈值过滤掉与 `ignored` 样本重合度过高的预测边界盒
|
||
|
||
值得注意的是,`pred_score_thrs` 默认将**自动搜索**一定范围内的**最佳阈值**,用户也可以通过手动修改配置文件来自定义搜索范围:
|
||
|
||
```python
|
||
# HmeanIOUMetric 默认以 0.1 为步长搜索 [0.3, 0.9] 范围内的最佳得分阈值
|
||
val_evaluator = dict(type='HmeanIOUMetric', pred_score_thrs=dict(start=0.3, stop=0.9, step=0.1))
|
||
```
|
||
|
||
2. 计算 IoU 矩阵
|
||
|
||
- 在数据处理阶段,`HmeanIOUMetric` 会计算并维护一个 {math}`M \times N` 的 IoU 矩阵 `iou_metric`,以方便后续的边界盒配对步骤。其中,M 和 N 分别为标签边界盒与过滤后预测边界盒的数量。由此,该矩阵的每个元素都存放了第 m 个标签边界盒与第 n 个预测边界盒之间的交并比(IoU)。
|
||
|
||
3. 基于相应的配对策略统计能被准确匹配的 GT 样本数
|
||
|
||
尽管 `HmeanIOUMetric` 可以由固定的公式计算取得,不同的任务或算法库内部的具体实现仍可能存在一些细微差别。这些差异主要体现在采用不同的策略来匹配真实与预测边界盒,从而导致最终得分的差距。目前,MMOCR 内部的 `HmeanIOUMetric` 共支持两种不同的匹配策略,即 `vanilla` 与 `max_matching`。如下所示,用户可以通过修改配置文件来指定不同的匹配策略。
|
||
|
||
- `vanilla` 匹配策略
|
||
|
||
`HmeanIOUMetric` 默认采用 `vanilla` 匹配策略,该实现与 MMOCR 0.x 版本中的 `hmean-iou` 及 ICDAR 系列**官方文本检测竞赛的评测标准保持一致**,采用先到先得的匹配方式对标签边界盒(Ground-truth bbox)与预测边界盒(Predicted bbox)进行配对。
|
||
|
||
```python
|
||
# 不指定 strategy 时,HmeanIOUMetric 默认采用 'vanilla' 匹配策略
|
||
val_evaluator = dict(type='HmeanIOUMetric')
|
||
```
|
||
|
||
- `max_matching` 匹配策略
|
||
|
||
针对现有匹配机制中的不完善之处,MMOCR 算法库实现了一套更高效的匹配策略,用以最大化匹配数目。
|
||
|
||
```python
|
||
# 指定采用 'max_matching' 匹配策略
|
||
val_evaluator = dict(type='HmeanIOUMetric', strategy='max_matching')
|
||
```
|
||
|
||
```{note}
|
||
我们建议面向学术研究的开发用户采用默认的 `vanilla` 匹配策略,以保证与其他论文的对比结果保持一致。而面向工业应用的开发用户则可以采用 `max_matching` 匹配策略,以获得精准的结果。
|
||
```
|
||
|
||
4. 根据上文介绍的 `HmeanIOUMetric` 公式计算最终的评测得分
|
||
|
||
### WordMetric
|
||
|
||
[WordMetric](mmocr.evaluation.metrics.recog_metric.WordMetric) 实现了**单词级别**的文本识别评测指标,并内置了 `exact`,`ignore_case`,及 `ignore_case_symbol` 三种文本匹配模式,用户可以在配置文件中修改 `mode` 字段来自由组合输出一种或多种文本匹配模式下的 `WordMetric` 得分。
|
||
|
||
```python
|
||
# 在文本识别任务中使用 WordMetric 评测
|
||
val_evaluator = [
|
||
dict(type='WordMetric', mode=['exact', 'ignore_case', 'ignore_case_symbol'])
|
||
]
|
||
```
|
||
|
||
- `exact`:全匹配模式,即,预测与标签完全一致才能被记录为正确样本。
|
||
- `ignore_case`:忽略大小写的匹配模式。
|
||
- `ignore_case_symbol`:忽略大小写及符号的匹配模式,这也是大部分学术论文中报告的文本识别准确率;MMOCR 报告的识别模型性能默认采用该匹配模式。
|
||
|
||
假设真实标签为 `MMOCR!`,模型的输出结果为 `mmocr`,则三种匹配模式下的 `WordMetric` 得分分别为:`{'exact': 0, 'ignore_case': 0, 'ignore_case_symbol': 1}`。
|
||
|
||
### CharMetric
|
||
|
||
[CharMetric](mmocr.evaluation.metrics.recog_metric.CharMetric) 实现了**不区分大小写**的**字符级别**的文本识别评测指标。
|
||
|
||
```python
|
||
# 在文本识别任务中使用 CharMetric 评测
|
||
val_evaluator = [dict(type='CharMetric')]
|
||
```
|
||
|
||
具体而言,`CharMetric` 会输出两个评测评测指标,即字符精度 `char_precision` 和字符召回率 `char_recall`。设正确预测的字符(True Positive)数量为 {math}`\sigma_{tp}`,则精度 *P* 和召回率 *R* 可由下式计算取得:
|
||
|
||
```{math}
|
||
P=\frac{\sigma_{tp}}{\sigma_{pred}}, R = \frac{\sigma_{tp}}{\sigma_{gt}}
|
||
```
|
||
|
||
其中,{math}`\sigma_{gt}` 与 {math}`\sigma_{pred}` 分别为标签文本与预测文本所包含的字符总数。
|
||
|
||
例如,假设标签文本为 "MM**O**CR",预测文本为 "mm**0**cR**1**",则使用 `CharMetric` 评测指标的得分为:
|
||
|
||
```{math}
|
||
P=\frac{4}{6}, R=\frac{4}{5}
|
||
```
|
||
|
||
### OneMinusNEDMetric
|
||
|
||
[`OneMinusNEDMetric(1-N.E.D)`](mmocr.evaluation.metrics.recog_metric.OneMinusNEDMetric) 常用于中文或英文**文本行级别**标注的文本识别评测,不同于全匹配的评测标准要求预测与真实样本完全一致,该评测指标使用归一化的[编辑距离](https://en.wikipedia.org/wiki/Edit_distance)(Edit Distance,又名莱温斯坦距离 Levenshtein Distance)来测量预测文本与真实文本之间的差异性,从而在评测长文本样本时能够更好地区分出模型的性能差异。假设真实和预测文本分别为 {math}`s_i` 和 {math}`\hat{s_i}`,其长度分别为 {math}`l_{i}` 和 {math}`\hat{l_i}`,则 `OneMinusNEDMetric` 得分可由下式计算得到:
|
||
|
||
```{math}
|
||
score = 1 - \frac{1}{N}\sum_{i=1}^{N}\frac{D(s_i, \hat{s_{i}})}{max(l_{i},\hat{l_{i}})}
|
||
```
|
||
|
||
其中,*N* 是样本总数,{math}`D(s_1, s_2)` 为两个字符串之间的编辑距离。
|
||
|
||
例如,假设真实标签为 "OpenMMLabMMOCR",模型 A 的预测结果为 "0penMMLabMMOCR", 模型 B 的预测结果为 "uvwxyz",则采用全匹配和 `OneMinusNEDMetric` 评测指标的结果分别为:
|
||
|
||
| | | |
|
||
| ------ | ------ | ---------- |
|
||
| | 全匹配 | 1 - N.E.D. |
|
||
| 模型 A | 0 | 0.92857 |
|
||
| 模型 B | 0 | 0 |
|
||
|
||
由上表可以发现,尽管模型 A 仅预测错了一个字母,而模型 B 全部预测错误,在使用全匹配的评测指标时,这两个模型的得分都为0;而使用 `OneMinuesNEDMetric` 的评测指标则能够更好地区分模型在**长文本**上的性能差异。
|
||
|
||
### F1Metric
|
||
|
||
[F1Metric](mmocr.evaluation.metrics.f_metric.F1Metric) 实现了针对 KIE 任务的 F1-Metric 评测指标,并提供了 `micro` 和 `macro` 两种评测模式。
|
||
|
||
```python
|
||
val_evaluator = [
|
||
dict(type='F1Metric', mode=['micro', 'macro'],
|
||
]
|
||
```
|
||
|
||
- `micro` 模式:依据 True Positive,False Negative,及 False Positive 总数来计算全局 F1-Metric 得分。
|
||
|
||
- `macro` 模式:依据类别标签计算每一类的 F1-Metric,并求平均值。
|
||
|
||
### 自定义评测指标
|
||
|
||
对于追求更高定制化功能的用户,MMOCR 也支持自定义实现不同类型的评测指标。一般来说,用户只需要新建自定义评测指标类 `CustomizedMetric` 并继承 {external+mmengine:doc}`MMEngine: BaseMetric <design/evaluation>`,然后分别重写数据格式处理方法 `process` 以及指标计算方法 `compute_metrics`。最后,将其加入 `METRICS` 注册器即可实现任意定制化的评测指标。
|
||
|
||
```python
|
||
from mmengine.evaluator import BaseMetric
|
||
from mmocr.registry import METRICS
|
||
|
||
@METRICS.register_module()
|
||
class CustomizedMetric(BaseMetric):
|
||
|
||
def process(self, data_batch: Sequence[Dict], predictions: Sequence[Dict]):
|
||
""" process 接收两个参数,分别为 data_batch 存放真实标签信息,以及 predictions
|
||
存放预测结果。process 方法负责将标签信息转换并存放至 self.results 变量中
|
||
"""
|
||
pass
|
||
|
||
def compute_metrics(self, results: List):
|
||
""" compute_metric 使用经过 process 方法处理过的标签数据计算最终评测得分
|
||
"""
|
||
pass
|
||
```
|
||
|
||
```{note}
|
||
更多内容可参见 {external+mmengine:doc}`MMEngine 文档: BaseMetric <design/evaluation>`。
|
||
```
|