词性标注器的输入是单词,输出是每个单词的词性标签。
tagger=hanlp.load(hanlp.pretrained.pos.PTB_POS_RNN_FASTTEXT_EN) tagger([[ I , banked , 2 , dollars , in , a , bank , . ],[ Is , this , the , future , of , chamber , music , ? ]])[[ PRP , VBD , CD , NNS , IN , DT , NN , . ],[ VBZ , DT , DT , NN , IN , NN , NN , . ]]
词性标注同样支持多语种,取决于你加载的是哪个模型(注意变量名后面的ZH)。
tagger=hanlp.load(hanlp.pretrained.pos.CTB5_POS_RNN_FASTTEXT_ZH) tagger([ 我 , 的 , 希望 , 是 , 希望 , 和平 ])[ PN , DEG , NN , VC , VV , NN ]
注意到句子中两个 希望的词性各不相同,第一个是名词而第二个是动词。关于词性标签,请参考《自然语言处理入门》第七章,或等待正式文档。这个标注器使用了fasttext1 作为嵌入层,所以免疫于OOV。
命名实体识别命名实体识别模块的输入是单词列表,输出是命名实体的边界和类别。
recognizer=hanlp.load(hanlp.pretrained.ner.CONLL03_NER_BERT_BASE_UNCASED_EN) recognizer([ President , Obama , is , speaking , at , the , White , House ])[( Obama , PER ,1,2),( WhiteHouse , LOC ,6,8)]
中文命名实体识别是字符级模型,所以不要忘了用 list将字符串转换为字符列表。至于输出,格式为 (entity, type, begin, end)。
recognizer=hanlp.load(hanlp.pretrained.ner.MSRA_NER_BERT_BASE_ZH) recognizer([list( 上海华安工业(集团)公司董事长谭旭光和秘书张晚霞来到美国纽约现代艺术博物馆参观。 ),list( 萨哈夫说,伊拉克将同联合国销毁伊拉克大规模杀伤性武器特别委员会继续保持合作。 )])[[( 上海华安工业(集团)公司 , NT ,0,12),( 谭旭光 , NR ,15,18),( 张晚霞 , NR ,21,24),( 美国 , NS ,26,28),( 纽约现代艺术博物馆 , NS ,28,37)],[( 萨哈夫 , NR ,0,3),( 伊拉克 , NS ,5,8),( 联合国销毁伊拉克大规模杀伤性武器特别委员会 , NT ,10,31)]]
这里的 MSRA_NER_BERT_BASE_ZH 是基于 BERT2的最准确的模型,你可以浏览该模型的评测指标:
$cat~/.hanlp/ner/ner_bert_base_msra_20200104_185735/test.log20-01-0418:55:02INFOEvaluationresultsfortest.tsv-loss:1.4949-f1:0.9522-speed:113.37sample/secprocessed177342tokenswith5268phrases;found:5316phrases;correct:5039.accuracy:99.37%;precision:94.79%;recall:95.65%;FB1:95.22NR:precision:96.39%;recall:97.83%;FB1:97.101357NS:precision:96.70%;recall:95.79%;FB1:96.242610NT:precision:89.47%;recall:93.13%;FB1:91.271349依存句法分析
句法分析是NLP的核心任务,在许多硬派的学者和面试官看来,不懂句法分析的人称不上NLP研究者或工程师。然而通过HanLP,只需两行代码即可完成句法分析。
syntactic_parser=hanlp.load(hanlp.pretrained.dep.PTB_BIAFFINE_DEP_EN) print(syntactic_parser([( Is , VBZ ),( this , DT ),( the , DT ),( future , NN ),( of , IN ),( chamber , NN ),( music , NN ),( ? , . )]))1 Is _ VBZ _ _ 4 cop _ _2 this _ DT _ _ 4 nsubj _ _3 the _ DT _ _ 4 det _ _4 future _ NN _ _ 0 root _ _5 of _ IN _ _ 4 prep _ _6 chamber _ NN _ _ 7 nn _ _7 music _ NN _ _ 5 pobj _ _8 ? _ . _ _ 4 punct _ _
句法分析器的输入是单词列表及词性列表,输出是 CoNLL-X 格式3的句法树,用户可通过 CoNLLSentence 类来操作句法树。一个中文例子:
syntactic_parser=hanlp.load(hanlp.pretrained.dep.CTB7_BIAFFINE_DEP_ZH) print(syntactic_parser([( 中国 , NR ),( 批准 , VV ),( 设立 , VV ),( 了 , AS ),( 三十万 , CD ),( 家 , M ),( 外商 , NN ),( 投资 , NN ),( 企业 , NN )]))1 中国 _ NR _ _ 2 nsubj _ _2 批准 _ VV _ _ 0 root _ _3 设立 _ VV _ _ 2 ccomp _ _4 了 _ AS _ _ 3 asp _ _5 三十万 _ CD _ _ 6 nummod _ _6 家 _ M _ _ 9 clf _ _7 外商 _ NN _ _ 9 nn _ _8 投资 _ NN _ _ 9 nn _ _9 企业 _ NN _ _ 3 dobj _ _
关于句法标签,请参考《自然语言处理入门》第11章,或等待正式文档。
语义依存分析语义分析结果为一个有向无环图,称为语义依存图(Semantic Dependency Graph)。图中的节点为单词,边为语义依存弧,边上的标签为语义关系。
semantic_parser=hanlp.load(hanlp.pretrained.sdp.SEMEVAL15_PAS_BIAFFINE_EN) print(semantic_parser([( Is , VBZ ),( this , DT ),( the , DT ),( future , NN ),( of , IN ),( chamber , NN ),( music , NN ),( ? , . )]))1 Is _ VBZ _ _ 0 ROOT _ _2 this _ DT _ _ 1 verb_ARG1 _ _3 the _ DT _ _ 0 ROOT _ _4 future _ NN _ _ 1 verb_ARG2 _ _4 future _ NN _ _ 3 det_ARG1 _ _4 future _ NN _ _ 5 prep_ARG1 _ _5 of _ IN _ _ 0 ROOT _ _6 chamber _ NN _ _ 0 ROOT _ _7 music _ NN _ _ 5 prep_ARG2 _ _7 music _ NN _ _ 6 noun_ARG1 _ _8 ? _ . _ _ 0 ROOT _ _
HanLP实现了最先进的biaffine4 模型,支持任意语种的语义依存分析:
semantic_parser=hanlp.load(SEMEVAL16_NEWS_BIAFFINE_ZH) print(semantic_parser([( 中国 , NR ),( 批准 , VV ),( 设立 , VV ),( 了 , AS ),( 三十万 , CD ),( 家 , M ),( 外商 , NN ),( 投资 , NN ),( 企业 , NN )]))1 中国 _ NR _ _ 2 Agt _ _1 中国 _ NR _ _ 3 Agt _ _2 批准 _ VV _ _ 0 Root _ _3 设立 _ VV _ _ 2 eProg _ _4 了 _ AS _ _ 3 mTime _ _5 三十万 _ CD _ _ 6 Quan _ _6 家 _ M _ _ 9 Qp _ _7 外商 _ NN _ _ 8 Agt _ _8 投资 _ NN _ _ 9 rDatv _ _9 企业 _ NN _ _ 2 Pat _ _9 企业 _ NN _ _ 3 Prod _ _
输出依然是 CoNLLSentence 格式,只不过这次是一个图,图中任意节点可以有零个或任意多个中心词,比如 中国 有两个中心词 (ID 2 和 3)。语义依存关系可参考《中文语义依存分析语料库》,或等待正式文档。
既然句法和语义分析依赖于词性标注,而词性标注又依赖于分词。如果有一种类似于计算图的机制自动将这些模块串联起来就好了。HanLP设计的流水线可以灵活地将多个组件(统计模型或规则系统)组装起来:
pipeline=hanlp.pipeline()\\.append(hanlp.utils.rules.split_sentence,output_key= sentences )\\.append(tokenizer,output_key= tokens )\\.append(tagger,output_key= part_of_speech_tags )\\.append(syntactic_parser,input_key=( tokens , part_of_speech_tags ),output_key= syntactic_dependencies )\\.append(semantic_parser,input_key=( tokens , part_of_speech_tags ),output_key= semantic_dependencies )
注意流水线的第一级管道是一个普通的Python函数 split_sentence,用来将文本拆分为句子。而input_key和output_key指定了这些管道的连接方式,你可以将这条流水线打印出来观察它的结构:
pipeline[None- LambdaComponent- sentences,sentences- NgramConvTokenizer- tokens,tokens- RNNPartOfSpeechTagger- part_of_speech_tags,( tokens , part_of_speech_tags )- BiaffineDependencyParser- syntactic_dependencies,( tokens , part_of_speech_tags )- BiaffineSemanticDependencyParser- semantic_dependencies]
这次,就像你在日常工作中最常见的场景一样,我们一次性输入一整篇文章 text:
print(pipeline(text)) sentences :[ JobsandWozniakco-foundedApplein1976tosellWozniak sAppleIpersonalcomputer. , TogethertheduogainedfameandwealthayearlaterwiththeAppleII. ], tokens :[[ Jobs , and , Wozniak , co-founded , Apple , in , 1976 , to , sell , Wozniak , s , , Apple , I , personal , computer , . ],[ Together , the , duo , gained , fame , and , wealth , a , year , later , with , the , Apple , II , . ]], part_of_speech_tags :[[ NNS , CC , NNP , VBD , NNP , IN , CD , TO , VB , NNP , POS , `` , NNP , PRP , JJ , NN , . ],[ IN , DT , NN , VBD , NN , CC , NN , DT , NN , RB , IN , DT , NNP , NNP , . ]], syntactic_dependencies :[[[4, nsubj ],[1, cc ],[1, conj ],[0, root ],[4, dobj ],[4, prep ],[6, pobj ],[9, aux ],[4, xcomp ],[16, poss ],[10, possessive ],[16, punct ],[16, nn ],[16, nn ],[16, amod ],[9, dobj ],[4, punct ]],[[4, advmod ],[3, det ],[4, nsubj ],[0, root ],[4, dobj ],[5, cc ],[5, conj ],[9, det ],[10, npadvmod ],[4, advmod ],[4, prep ],[14, det ],[14, nn ],[11, pobj ],[4, punct ]]], semantic_dependencies :[[[[2],[ coord_ARG1 ]],[[4,9],[ verb_ARG1 , verb_ARG1 ]],[[2],[ coord_ARG2 ]],[[6,8],[ prep_ARG1 , comp_MOD ]],[[4],[ verb_ARG2 ]],[[0],[ ROOT ]],[[6],[ prep_ARG2 ]],[[0],[ ROOT ]],[[8],[ comp_ARG1 ]],[[11],[ poss_ARG2 ]],[[0],[ ROOT ]],[[0],[ ROOT ]],[[0],[ ROOT ]],[[0],[ ROOT ]],[[0],[ ROOT ]],[[9,11,12,14,15],[ verb_ARG3 , poss_ARG1 , punct_ARG1 , noun_ARG1 , adj_ARG1 ]],[[0],[ ROOT ]]],[[[0],[ ROOT ]],[[0],[ ROOT ]],[[1,2,4],[ adj_ARG1 , det_ARG1 , verb_ARG1 ]],[[1,10],[ adj_ARG1 , adj_ARG1 ]],[[6],[ coord_ARG1 ]],[[4],[ verb_ARG2 ]],[[6],[ coord_ARG2 ]],[[0],[ ROOT ]],[[8],[ det_ARG1 ]],[[9],[ noun_ARG1 ]],[[0],[ ROOT ]],[[0],[ ROOT ]],[[0],[ ROOT ]],[[11,12,13],[ prep_ARG2 , det_ARG1 , noun_ARG1 ]],[[0],[ ROOT ]]]]}
中文处理和英文一模一样,事实上,HanLP2.0认为所有人类语言都是统一的符号系统:
print(pipeline(text)) sentences :[ HanLP是一系列模型与算法组成的自然语言处理工具包,目标是普及自然语言处理在生产环境中的应用。 , HanLP具备功能完善、性能高效、架构清晰、语料时新、可自定义的特点。 , 内部算法经过工业界和学术界考验,配套书籍《自然语言处理入门》已经出版。 ], tokens :[[ HanLP , 是 , 一 , 系列 , 模型 , 与 , 算法 , 组成 , 的 , 自然 , 语言 , 处理 , 工具包 , , , 目标 , 是 , 普及 , 自然 , 语言 , 处理 , 在 , 生产 , 环境 , 中 , 的 , 应用 , 。 ],[ HanLP , 具备 , 功能 , 完善 , 、 , 性能 , 高效 , 、 , 架构 , 清晰 , 、 , 语料 , 时 , 新 , 、 , 可 , 自 , 定义 , 的 , 特点 , 。 ],[ 内部 , 算法 , 经过 , 工业界 , 和 , 学术界 , 考验 , , , 配套 , 书籍 , 《 , 自然 , 语言 , 处理 , 入门 , 》 , 已经 , 出版 , 。 ]], part_of_speech_tags :[[ NR , VC , CD , M , NN , CC , NN , VV , DEC , NN , NN , VV , NN , PU , NN , VC , VV , NN , NN , VV , P , NN , NN , LC , DEG , NN , PU ],[ NR , VV , NN , VA , PU , NN , VA , PU , NN , VA , PU , NN , LC , VA , PU , VV , P , VV , DEC , NN , PU ],[ NN , NN , P , NN , CC , NN , NN , PU , VV , NN , PU , NN , NN , NN , NN , PU , AD , VV , PU ]], syntactic_dependencies :[[[2, top ],[0, root ],[4, nummod ],[11, clf ],[7, conj ],[7, cc ],[8, nsubj ],[11, rcmod ],[8, cpm ],[11, nn ],[12, nsubj ],[2, ccomp ],[12, dobj ],[2, punct ],[16, top ],[2, conj ],[16, ccomp ],[19, nn ],[20, nsubj ],[17, conj ],[26, assmod ],[23, nn ],[24, lobj ],[21, plmod ],[21, assm ],[20, dobj ],[2, punct ]],[[2, nsubj ],[0, root ],[4, nsubj ],[20, rcmod ],[4, punct ],[7, nsubj ],[4, conj ],[4, punct ],[10, nsubj ],[4, conj ],[4, punct ],[13, lobj ],[14, loc ],[4, conj ],[4, punct ],[18, mmod ],[18, advmod ],[4, conj ],[4, cpm ],[2, dobj ],[2, punct ]],[[2, nn ],[18, nsubj ],[18, prep ],[6, conj ],[6, cc ],[7, nn ],[3, pobj ],[18, punct ],[10, rcmod ],[15, nn ],[15, punct ],[15, nn ],[15, nn ],[15, nn ],[18, nsubj ],[15, punct ],[18, advmod ],[0, root ],[18, punct ]]], semantic_dependencies :[[[[2],[ Exp ]],[[0],[ Aft ]],[[4],[ Quan ]],[[0],[ Aft ]],[[8],[ Poss ]],[[7],[ mConj ]],[[8],[ Datv ]],[[11],[ rProd ]],[[8],[ mAux ]],[[11],[ Desc ]],[[12],[ Datv ]],[[2],[ dClas ]],[[2,12],[ Clas , Cont ]],[[2,12],[ mPunc , mPunc ]],[[16],[ Exp ]],[[17],[ mMod ]],[[2],[ eSucc ]],[[19],[ Desc ]],[[20],[ Pat ]],[[26],[ rProd ]],[[23],[ mPrep ]],[[23],[ Desc ]],[[20],[ Loc ]],[[23],[ mRang ]],[[0],[ Aft ]],[[16],[ Clas ]],[[16],[ mPunc ]]],[[[2],[ Poss ]],[[0],[ Aft ]],[[4],[ Exp ]],[[0],[ Aft ]],[[4],[ mPunc ]],[[0],[ Aft ]],[[4],[ eCoo ]],[[4,7],[ mPunc , mPunc ]],[[0],[ Aft ]],[[0],[ Aft ]],[[7,10],[ mPunc , mPunc ]],[[0],[ Aft ]],[[12],[ mTime ]],[[0],[ Aft ]],[[14],[ mPunc ]],[[0],[ Aft ]],[[0],[ Aft ]],[[20],[ Desc ]],[[18],[ mAux ]],[[0],[ Aft ]],[[0],[ Aft ]]],[[[2],[ Desc ]],[[7,9,18],[ Exp , Agt , Exp ]],[[4],[ mPrep ]],[[0],[ Aft ]],[[6],[ mPrep ]],[[7],[ Datv ]],[[0],[ Aft ]],[[7],[ mPunc ]],[[7],[ eCoo ]],[[0],[ Aft ]],[[0],[ Aft ]],[[13],[ Desc ]],[[0],[ Aft ]],[[0],[ Aft ]],[[0],[ Aft ]],[[0],[ Aft ]],[[18],[ mTime ]],[[0],[ Aft ]],[[18],[ mPunc ]]]]}
输出为一个json化的 dict,大部分用户应当很熟悉。
本文链接: http://jlpcorp.immuno-online.com/view-720744.html