TextRank是受到Google的PageRank的启发,通过把文本分割成若干组成单元(单词、句子)并建立图模型, 利用投票机制对文本中的重要成分进行排序, 仅利用单篇文档本身的信息即可实现关键词提取、文本摘要抽取。

PageRank

PageRank是用来标识网页的等级、 重要性的一种方法, 是衡量一个网页的重要指标。PageRank 算法提出之前, 已经有人提出使用网页的入链数量进行链接分析, 但是PageRank算法除了考虑入链数量之外, 还参考了网页质量因素, 通过组合入链数量和网页质量因素两个指标, 使得网页重要性的评价更加准确。

PageRank计算公式

nltk 文本摘要 textrank 摘要_相似度

nltk 文本摘要 textrank 摘要_权重_02

是网页i的中重要性(PR值)。d是阻尼系数,一般设置为0.85。

是存在指向网页i的链接的网页集合。

是网页j中的链接存在的链接指向的网页的集合。

nltk 文本摘要 textrank 摘要_nltk 文本摘要_03

是集合中元素的个数。

TextRankTextRank 提取关键字

将原文本拆分为句子,在每个句子中过滤掉停用词(可选),并只保留指定词性的单词(可选)。由此可以得到句子的集合和单词的集合。

每个单词作为pagerank中的一个节点。设定窗口大小为kk,假设一个句子依次由下面的单词组成:

 。

nltk 文本摘要 textrank 摘要_相似度_04

  等都是一个窗口。在一个窗口中的任两个单词对应的节点之间存在一个无向无权的边。

基于上面构成图,可以计算出每个单词节点的重要性。最重要的若干单词可以作为关键词。

 

TextRank 提取摘要

句子节点的权值更新公式:

nltk 文本摘要 textrank 摘要_nltk 文本摘要_05

  • 句子相似度:

nltk 文本摘要 textrank 摘要_nltk 文本摘要_06

等式左边表示一个句子的权重(WS 是 weight_sum 的缩写),右侧的求和表示每个相邻句子对本句子的贡献程度。与提取关键字的时候不同,一般认为全部句子都是相邻的,不再通过窗口提取。

边的权值 

nltk 文本摘要 textrank 摘要_相似度_07

代表句子 

nltk 文本摘要 textrank 摘要_4s_08

的相似度,既可以使用上面介绍过的基于句子间内容覆盖率的方法计算,也可以使用基于编辑距离,基于语义词典,余弦相似度,BM25 算法等等。

因为我们是要抽取关键句,因而是以句子为基本单位。使用 TextRank 提取摘要的整个过程如下:

  1. 预处理:将文本分割成句子以句子为节点构建图。
  2. 计算句子相似度:对句子进行分词、取停用词等处理,以便于计算任意两个句子之间的相似度。将计算好的句子相似度作为两个句子构成的边的权值。
  3. 句子权重:根据公式,迭代传播权重计算各句子的得分。
  4. 抽取文摘句:得到的句子得分进行倒序排序,抽取重要度最高的 N 个句子作为候选文摘句。
  5. 形成文摘:根据字数或句子数要求,从候选文摘句中抽取句子组成文摘。

Python实现TextRank

# -*- encoding:utf-8 -*-

import codecs
from textrank4zh import TextRank4Keyword, TextRank4Sentence

text = codecs.open('./text/01.txt', 'r', 'utf-8').read()
tr4w = TextRank4Keyword(stop_words_file='./stopword.data')  # 导入停止词

# 使用词性过滤,文本小写,窗口为2
tr4w.train(text=text, speech_tag_filter=True, lower=True, window=2)  

print '关键词:'
# 20个关键词且每个的长度最小为1
print '/'.join(tr4w.get_keywords(20, word_min_len=1))  

print '关键短语:'
# 20个关键词去构造短语,短语在原文本中出现次数最少为2
print '/'.join(tr4w.get_keyphrases(keywords_num=20, min_occur_num= 2))  

tr4s = TextRank4Sentence(stop_words_file='./stopword.data')

# 使用词性过滤,文本小写,使用words_all_filters生成句子之间的相似性
tr4s.train(text=text, speech_tag_filter=True, lower=True, source = 'all_filters')

print '摘要:'
print '\n'.join(tr4s.get_key_sentences(num=3)) # 重要性最高的三个句子