🧠 第六章 自然语言处理
📄 一句话概括

8 句同主题短文,词频打分选出第 5、6、7 句,TextRank 也选出第 5、6、7 句,重合 3 / 3, 两种打分的秩相关 1.000。摘要 47 字,压缩比 33.3%——换算法一点没变。

📝 本节和前面几节的关系

上一节做翻译,这一节做摘要。 同一族的生成任务,但摘要多了一个「选」的动作,而这个「选」正好能暴露算法的差别。

一、抽取式摘要的两套打分

上一章的网页摘要用的是词频打分:句子里含的高频 bigram 越多,分越高。 这一节加一个对照:TextRank。 它把句子当节点,句子之间的相似度当边的权重,然后在这个图上做迭代,谁的「票」多谁重要。 TextRank 的迭代式很简单:每个节点的新分数等于邻居分数的加权和,再混一点随机跳转(0.15), 迭代 30 次就稳了。 这个思路抄自网页排名。区别是网页靠链接投票,句子靠相似度投票。

二、结果:两种方法选出同一组

词频选第 5、6、7 句,TextRank 也选第 5、6、7 句,重合 3 / 3。 秩相关 1.000——不只是选出来的三句一样,整个 8 句的排序都几乎一致。 这不是巧合。TextRank 的边权是句子相似度,而句子相似度主要由词面重叠决定;词频打分也是数词面重叠。 两者是同源的。 所以「换一个更高级的算法」在这组数据上收益是零。这句话不好听,但是真的。 要拉开差距,得让相似度不再是字面重叠——比如用词向量算相似度,或者把语料换成话题更分散的长文。

三、TextRank 的两个毛病

  1. 它会偏向「和谁都像」的句子。 一句正确的废话(比如「以上是本期全部内容」)和每句都像,票数很高。
  2. 它对长度不敏感。长句天然和更多句子有重叠,容易刷票。 Demo 里第 6 句 21 字,得分 0.1913 最高,就吃了这个便宜。 词频打分的毛病正好相反:它偏向「主题词堆得多」的句子,容易选出几句意思重复的。 所以真实系统通常两个都用:TextRank 保证覆盖,再加一步冗余惩罚去重。

四、33.3% 的压缩比说明了什么

原文 141 字,摘要 47 字。这个比例比上一章网页那个 66.2% 好得多,但别高兴——分母不一样。 上一章那篇网页的 5 句里有 3 句入选,这一节 8 句里选 3 句,选的比例本来就低。 真正决定压缩比的是「选几句」,不是「用什么算法选」。想压得更狠,只能改写(生成式),不能只挑。 这也是为什么摘要产品最后都会走向「抽取加改写」:先选句保证不跑偏,再改写压字数。两段各管一件事。

五、动手 Demo:词频打分与 TextRank:两套选句算法对照

8 句同一主题的短文;先用 bigram 词频给每句打分,取前三; 再把句子两两算余弦建成 8×8 的图,行归一化后按 0.15 跳转概率迭代 30 次,取前三; 最后比两套结果的重合数、秩相关和压缩比。

M[i, j] = cos_bg(SENTS061[i], SENTS061[j])
M = M / M.sum(1, keepdims=True)          # 行归一化

p = np.ones(n) / n
for _ in range(30):
    p = 0.15 / n + 0.85 * (M.T @ p)      # 幂迭代

实跑输出:

--------------------------------------------------------------------
自动摘要:词频打分与 TextRank 的选句差异
--------------------------------------------------------------------
  句子数                   8
  句   内容(截断)                       词频分   TextRank   词频选   图选
  ------------------------------------------------------------------------
  1    近年来多地推进城市夜间照明节能改    1.056     0.0623
  2    传统高压钠灯正在被替换为LED光       1.000     0.0187
  3    据某市城建部门统计主城区路灯年耗    1.000     0.0187
  4    不过也有居民反映部分路段亮度过高    1.176     0.1206
  5    过高的亮度会影响临街住户休息        1.200     0.1229     是      是
  6    业内人士建议建立亮度分区标准        1.333     0.1913     是      是
  7    分区标准要按道路等级和周边环境分    1.200     0.1531     是      是
  8    目前该市已完成三轮改造涉及道路一    1.091     0.0998

  词频选中的句子           5、6、7
  TextRank 选中的          5、6、7
  重合                     3 / 3
  原文总字数               141
  图选的摘要字数           47(压缩比 33.3%)
  词频选的摘要字数         47(压缩比 33.3%)
  两种打分的秩相关         1.000

  这一组数据上,两套算法选出的三句完全是同一组——秩相关 1.000,说明它们的排序几乎一致。
  原因不难看出:TextRank 用的是句子之间的相似度,而句子之间的相似度又主要由词面重叠决定,跟词频打分本来就是同源的。
  所以「换更高级的算法」在小语料上收益很小。要拉开差距,得靠句子更多、更参差,或者引入词向量算相似度。

两张分数量级差很多:词频分在 1.0 到 1.3 之间,TextRank 在 0.019 到 0.191 之间。 量级不同不影响排序,但看表时容易误以为 TextRank 的差别更小。 第 6 句两项都排第一:词频 1.333、TextRank 0.1913。 它含「亮度分区标准」这个主题短语,又是全篇最长的句子之一。 第 5 句和第 7 句也是两项都高,所以三句全同。 第 2、3 句两项都最低(0.0187),它们只提到具体灯具和统计数据,和别的句子字面重叠少。 秩相关我算的是排序后的相关系数,1.000 表示两个排序完全一致。 这个数比「重合 3 / 3」更严格——它连没入选的句子顺序也一样。

30 秒实验

  1. 把跳转概率从 0.15 改成 0.5,看选出的三句会不会变。
  2. 把句子数从 8 增到 16(加 8 句别的主题),看两套算法还重不重合。
  3. 想一想:为什么「和谁都像」的句子在 TextRank 里得分高?

常见误区

  1. 「TextRank 比词频高级」——同源的时候收益是零,这一节就是证据。
  2. 「压缩比越低越好」——压得越狠越容易丢限定词。
  3. 「选句算法能替代改写」——抽取式压不动,要压必须改写。
自测三问(点开对答案) 1. TextRank 里「票」是怎么来的? —— 句子之间的相似度当边权,邻居的分加权求和,再混 0.15 的随机跳转。 2. 为什么这一节两套算法结果完全一样? —— 边权是字面相似度,词频打分也数字面重叠,两者同源。 3. TextRank 偏向什么样的句子? —— 和很多句子都像的、以及篇幅长的句子。

五类场景走完了。这一章最后五节是实战:从零训练一个 Embedding 模型。

相关笔记