【问题标题】:Evaluation in a Spacy NER modelSpacy NER 模型中的评估
【发布时间】:2017-12-03 07:40:51
【问题描述】:

我正在尝试评估使用 spacy lib 创建的经过训练的 NER 模型。 通常对于这类问题,您可以使用 f1 分数(准确率和召回率之间的比率)。我在文档中找不到训练有素的 NER 模型的准确度函数。

我不确定它是否正确,但我正在尝试通过以下方式(示例)并使用来自sklearnf1_score

from sklearn.metrics import f1_score
import spacy
from spacy.gold import GoldParse


nlp = spacy.load("en") #load NER model
test_text = "my name is John" # text to test accuracy
doc_to_test = nlp(test_text) # transform the text to spacy doc format

# we create a golden doc where we know the tagged entity for the text to be tested
doc_gold_text= nlp.make_doc(test_text)
entity_offsets_of_gold_text = [(11, 15,"PERSON")]
gold = GoldParse(doc_gold_text, entities=entity_offsets_of_gold_text)

# bring the data in a format acceptable for sklearn f1 function
y_true = ["PERSON" if "PERSON" in x else 'O' for x in gold.ner]
y_predicted = [x.ent_type_ if x.ent_type_ !='' else 'O' for x in doc_to_test]
f1_score(y_true, y_predicted, average='macro')`[1]
> 1.0

任何想法或见解都是有用的。

【问题讨论】:

    标签: python spacy


    【解决方案1】:

    您可以在spaCy/scorer.py 中找到不同的指标,包括 F 分数、召回率和准确率。

    这个例子展示了如何使用它:

    import spacy
    from spacy.gold import GoldParse
    from spacy.scorer import Scorer
    
    def evaluate(ner_model, examples):
        scorer = Scorer()
        for input_, annot in examples:
            doc_gold_text = ner_model.make_doc(input_)
            gold = GoldParse(doc_gold_text, entities=annot)
            pred_value = ner_model(input_)
            scorer.score(pred_value, gold)
        return scorer.scores
    
    # example run
    
    examples = [
        ('Who is Shaka Khan?',
         [(7, 17, 'PERSON')]),
        ('I like London and Berlin.',
         [(7, 13, 'LOC'), (18, 24, 'LOC')])
    ]
    
    ner_model = spacy.load(ner_model_path) # for spaCy's pretrained use 'en_core_web_sm'
    results = evaluate(ner_model, examples)
    

    scorer.scores 返回多个分数。运行示例时,结果如下所示:(请注意,出现低分是因为示例将伦敦和柏林分类为“LOC”,而模型将它们分类为“GPE”。您可以通过查看ents_per_type 来了解这一点.)

    {'uas': 0.0, 'las': 0.0, 'las_per_type': {'attr': {'p': 0.0, 'r': 0.0, 'f': 0.0}, 'root': {'p': 0.0, 'r': 0.0, 'f': 0.0}, 'compound': {'p': 0.0, 'r': 0.0, 'f': 0.0}, 'nsubj': {'p': 0.0, 'r': 0.0, 'f': 0.0}, 'dobj': {'p': 0.0, 'r': 0.0, 'f': 0.0}, 'cc': {'p': 0.0, 'r': 0.0, 'f': 0.0}, 'conj': {'p': 0.0, 'r': 0.0, 'f': 0.0}}, 'ents_p': 33.33333333333333, 'ents_r': 33.33333333333333, 'ents_f': 33.33333333333333, 'ents_per_type': {'PERSON': {'p': 100.0, 'r': 100.0, 'f': 100.0}, 'LOC': {'p': 0.0, 'r': 0.0, 'f': 0.0}, 'GPE': {'p': 0.0, 'r': 0.0, 'f': 0.0}}, 'tags_acc': 0.0, 'token_acc': 100.0, 'textcat_score': 0.0, 'textcats_per_cat': {}}
    

    示例取自spaCy example on github(链接不再有效)。上次使用 spacy 2.2.4 测试。

    【讨论】:

    • 您能否确认这仍然有效(对于 v2)?我在gold = GoldParse(doc_gold_text, entities=annot) 收到一个 KeyError
    • 此时我也遇到了错误。 gold = GoldParse(doc_gold_text, entities=_) File "gold.pyx", line 418, in spacy.gold.GoldParse.__init__ KeyError: 0
    • 我在网站上查看过,新版本似乎改变了这一点。 spacy.io/usage/v2 。我还没有找到解决办法。
    • @EvanLalo 确保 annot 是可迭代的元组,而不是字典。我遇到了同样的问题。
    • 试试这个entities=annot['entities'],而不是默认的entities=annot
    【解决方案2】:

    由于我遇到了同样的问题,我将在此处发布已接受答案中显示的示例代码,但对于 spacy V3:

    import spacy
    from spacy.scorer import Scorer
    from spacy.tokens import Doc
    from spacy.training.example import Example
    
    examples = [
        ('Who is Shaka Khan?',
         {(7, 17, 'PERSON')}),
        ('I like London and Berlin.',
         {(7, 13, 'LOC'), (18, 24, 'LOC')})
    ]
    
    def evaluate(ner_model, examples):
        scorer = Scorer()
        example = []
        for input_, annot in examples:
            pred = ner_model(input_)
            print(pred,annot)
            temp = Example.from_dict(pred, dict.fromkeys(annot))
            example.append(temp)
        scores = scorer.score(example)
        return scores
    
    ner_model = spacy.load('en_core_web_sm') # for spaCy's pretrained use 'en_core_web_sm'
    results = evaluate(ner_model, examples)
    print(results)
    

    由于不推荐使用诸如 goldParse 之类的库,因此发生了重大更改

    我相信关于指标的部分答案仍然有效

    【讨论】:

      【解决方案3】:

      请注意,在 spaCy v3 中有一个 evaluate command,您可以从命令行轻松使用,而不是编写自定义代码来处理事情。

      【讨论】:

        猜你喜欢
        • 2020-01-04
        • 2020-02-03
        • 1970-01-01
        • 1970-01-01
        • 2023-03-07
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多