深度探索Deep_NLP及其Python实现(二):NLP常见指标小结

Posted by nickiwei on April 29, 2018

这个系列从最基础的word2vec开始, 从零开始实现深度网络在NLP领域的各类模型及其应用。 本系列要求读者对深度神经网络有基础的理解(如全连接网络, 卷积网络)等。

欢迎转载, 转载请注明出处及链接。

完整代码库请查看我的GithubRepo: https://github.com/nick6918/MyNLP .部分代码参考了Stanford CS224n 课程作业。

准召平衡

在一般分类问题中, 我们常用的所有指标如下:

ConMx

样本的真实0/1分类(True Class)和机器分类(Hypothesized Class)组成了一个2*2矩阵, 称之为混淆矩阵。

我们通常关心判准和判全两个指标, 也就是准确率(precision)和召回率(Recall)

  • Precision

准确率: 所有判定为Positive的样本中有多少判对了的。

  • Recall

召回率: 所有Positive样本中, 有多少被判出了。俗称判全率。

可以看出, 准确和召回是一组相互影响的指标, 通常情况下, 准确上升必然导致召回下降, 反之亦然。 为了综合选择准召效果最好的一组, 也就是进行准召平衡, 我们引入F1 score(图中的F measure).

通常情况下, 选择F measure最高的一组参数, 但在业务中, 我们会遇到更偏重于准确或者更偏重于召回的情况, 这种情况下也可以对F measure 加权或者直接看准召独立数据。 按需取用即可。

另一组二值分类指标:ROC与AUC

TPR和FPR

在前一部分, 我们已经介绍了准召指标及F1 score, 除此之外, 我们还有另外两个指标. FPR和TPR.

  • FPR (False Positive Rate)

FPR: 用来计算假阳性在所有阴性中的占比。

  • TPR (True Positive Rate)

TPR就是Recall. 用来计算所有阳性中, 被发现的阳性 在所有阳性中的占比。

ROC曲线

假设我们关心的是阳性被更“正确地”判定出来, 那么准召是更适合需求的指标。FPR和TPR这组指标看似直接利用价值不大, 但是他引入了另一个非常重要的指标: ROC曲线。 一个典型的ROC曲线如下:

ConMx

如何理解FPR, TPR, ROC这三个指标呢? 首先, FPR和TPR将数据按照其真实分类分成两个完全独立的部分,在Positive数据中看正确被判出的几率, 在Negative 数据中看错误被判为阳性的几率, 然后利用ROC曲线将这两组数据结合在一起。

为了充分理解这个模型, 我们再来看四个极值点:

(0, 0) : 所有样本均判定为 Negative (1, 1) : 所有样本均判定为 Positive (0.5, 0.5): 正负样本均有一半被判定正确。 (0, 1): 所有样本均被判定正确。 (1, 0): 所有样本均被错误判定。

在看一个随机点:

(0.2, 0.2): 模型将20%的阳性数据判为了阳性, 模型将20%的阴性数据判为了阳性。

综上, ROC曲线将TPR和FPR这两个数据结合在一起来看,模型分别将多少阳性和阴性数据判定为了阳性。 特别值得注意的:

  • 模型越靠近(1, 1)点(右上角), 就有越多数据被判定为了阳性。
  • 模型越靠近(0, 1)点(左上角), 模型的综合准确率就越高。

但ROC毕竟是一条曲线, 我们如何使用这条曲线来判断模型的优劣呢? 为此, 我们引入AUC指标。

ROC曲线定义和绘制

我们知道, 当我们得到一组分类结果和混淆矩阵后, 只能得到一组(TPR, FPR), 但是ROC是一条曲线, 意味着我们需要若干个这样的数据对, 那么, ROC曲线是如何得到的呢?

我们再来看ROC曲线的定义: ROC曲线实际上是当分类器阀值变化的时候, TPR/FPR的比率变化曲线。

因此, 为了绘制ROC, 我们需要尽可能细的调整threshhold, 然后得到若干混淆矩阵, 计算比值, 绘制曲线。 这一过程由计算机完成的还是比较简洁明了的。

最后, 我们还要引入ROC曲线最重要的两个特性:

1, 当测试集中的正负样本的分布变化的时候,ROC曲线能够保持不变。

其实很好理解, 因为TPR和FPR将正负样本数据进行了独立计算, 所以不会收到样本比例变化的影响。 反之, 在计算准召时, 如果样本比例发生变化, 那么准召特别是召回会产生较大的变动。

这个特性的意义在于, 当我们改变数据集的构成(例如增加数据, 添加数据层面上的Data Augmentation等), 所得到的AUC仍然可以直接比较。

2, ROC的计算与阀值无关

在计算准召时, 我们需要使用一个阀值(一般是0.5)将概率转化为分类, 然后计算准召。 但是在实际模型调试的过程中, 不同的参数对应的最有threshhold可能不一致, 这就要求我们不断调整阀值, 给模型训练增加了难度。

这两个核心特性即样本比例无关性和阀值无关性使得ROC曲线称为描述模型本身性能的最好指标, 但是ROC曲线毕竟是一条曲线, 我们很难判定怎样的ROC曲线是更好的曲线, 为此, 我们引入AUC指标。

AUC

我们其实更关心的不是ROC上的某一个点, 而是ROC曲线下方的面积。这个面积的取值范围恰为(0, 1), 被称之为AUC(Area Under Curve). 实际上, AUC一般是在(0.5, 1)波动。

如何理解AUC呢?从定义来理解AUC的含义,比较困难。 我们试图从另一角度来解读AUC。

AUC可以理解为从1样本中选择一个样本, 从0样本中选择一个样本, 1样本被判定为1的概率为P1, 0样本被判定为1的概率为P0, P1 > P0的概率即为AUC。

可见, AUC为1 当且仅当 1样本100%被判定为1, 0样本100%被判定为0, 模型正确率100%.

当AUC为0.5, 如下图, 我们可以看出, 无论threshhold设为多少, 模型均有一半概率将1样本或者0样本判定为1, 模型完全随机判定。

AUC0.5

更常见的ROC曲线如下图所示, 不同threshhold下, 模型取得的比例是不一致的, 但一般均大于0.5, 在某一threshhold下,模型取得最接近于(0, 1)的比值。 整体而言, AUC大于0.5.

AUCBigger0.5

AUC 与 准召

以上两组指标, AUC和准召均描述二值分类模型指标, 那么, 二者如何区分呢?

我的理解是, AUC是更接近于描述模型学习性能的指标, 他排除了样本分布, 阀值选择这些外部因素, 单纯来看模型的学习效果。

而准召则更偏重于业务指标,他描述了模型对当前业务的实际效果, 即测试样本下对目标指标的判定能力。

准召数据对于业务是有直接意义的, 而AUC则没有。

在工程实践中, 我们会首先用AUC来调整模型的性能, 然后再当前模型下, 选择多个阀值, 计算准召。

翻译准确度:BLEU与CAR

ngram BLUE

在NLP相关问题中, 除了文本分类问题之外, 还有另一类问题, 即文本生成问题。 这类问题均以翻译模型Seq2Seq为基础, 使用有标数据进行训练。 在生成问题中, 最重要的机器判定指标就是BLEU了。

在BLEU之前, 一个显然的问题是, 如何通过非人工的方式判定翻译的准确性呢? 一个简单的指标是WER, 即词与词的比较是否一致。 容易想象, 词序, 近义词等都可能让这个指标产生巨大的误差。

BLEU的思路是, 从词贡献频率开始:

P = m / wt

m是词共现的数量, 即所有在机器翻译中的词在label翻译中也出现了的个数, wt是机器翻译中的词总量。

举例而言,

人类翻译: the cat is on the mat

机器翻译: cat at the mat

P = 3 / 4 = 0.75

但这个指标有一些问题, 如下例:

人类翻译: the cat is on the mat

机器翻译: the the the the the the the the

P = 7 / 7 = 1

可见, 词共现频率P有两个问题:

1, 非稀有词(the) 容易出现。

2, 多次重复计算

为此, 我们引入的第一个改进是 用ngram代替词, 事实上, 这不仅仅是防止非稀有词过度计算, 而且在语义上也是更直接的。比如take on 和take off是完全不一样的语义, 在翻译中就是应当整体计算。

再看一下上例:

人类翻译: the cat is on the mat

机器翻译: the the the the the the the

P = 0

另一个翻译:

人类翻译: the cat is on the mat

机器翻译: the the cat

2gram P = 1(the cat) / 2(the the, the cat) = 0.5

最后还有一个小修正, 所有label翻译中的ngram只能被使用一次, 这主意是为了防止语义被重复翻译:

人类翻译: the cat is on the mat

机器翻译: the cat the cat

2gram P = 2(the cat重复命中) / 3 = 0.67

Modified 2gram P = 1(the cat 只计算一次共现) / 3 = 0.33

BP(Brevity Penalty)

这样我们仍然面临一个问题, 那就是我们不需要翻译出原句中的全部语义, 只需要准确的翻译出部分语义, 就能得到一个很高的分数。

为此, BLEU还引入了短句惩罚BP(Brevity Penalty)

BP = min(exp(1-r/c), 1)

其中, C是机器译文的长度, r是人工label译文的长度, 可见, 当c<r时, BP值<1, 最终的分值变小已作惩罚(BLEU值越大越好)

综上, 我们最后给出BLEU的定义

BLEU

wn是ngram的倒数。 特别的, 当ngram=4时的log值, 是一个非常常用的指标, 简称BLEU4.

值得注意的是我们这里计算的是整个corpus的blue值, 而不是一句话的BLEU值。单独一句话的BLEU值考虑到召回的问题意义不大。

此外, BLEU值受语料影响, 不同数据的BLEU值之间没有比较价值。

CAR(Corpus Average Recall)

如上所说, BLEU只考虑翻译的准确度, 在召回方面, 只通过BP对短翻译做了penalty, 并没有只要度量模型对目标翻译中的语义命中情况。 为此, 我们引入辅助指标Recall, 同时, 为了与BLEU保持一致, 我们计算整个Corpus的平均Recall.

具体的计算方式

BLEU

BLEU

与BLEU相比, 只是把机器翻译句中的ngram数换成了 label翻译中的ngram数, 同时不进行BP惩罚。

CAR有其自身问题, 比如人工翻译中的语义并不一定全部完整且不多余的表达原句中的语义, 同时, 不区分关键语义等, 但作为辅助BLEU的一个指标, 有其存在的价值。

结语

在本文中, 我们介绍了文本分类和文本生成类问题中最常用的三大类指标, 在本系列的后几篇文章介绍相关模型及其应用中, 我们会经常见到这些指标。同时, 熟悉这些指标的原理对我们在调试模型时对症下药有着非常重要的意义。