专栏首页python3用Python进行简单的文本相似度分析

用Python进行简单的文本相似度分析

学习目标:

  1. 利用gensim包分析文档相似度
  2. 使用jieba进行中文分词
  3. 了解TF-IDF模型

环境:

Python 3.6.0 |Anaconda 4.3.1 (64-bit)

工具:

jupyter notebook

注:为了简化问题,本文没有剔除停用词“stop-word”。实际应用中应该要剔除停用词。

首先引入分词API库jieba、文本相似度库gensim

import jieba
from gensim import corpora,models,similarities

以下doc0-doc7是几个最简单的文档,我们可以称之为目标文档,本文就是分析doc_test(测试文档)与以上8个文档的相似度。

doc0 = "我不喜欢上海"
doc1 = "上海是一个好地方"
doc2 = "北京是一个好地方"
doc3 = "上海好吃的在哪里"
doc4 = "上海好玩的在哪里"
doc5 = "上海是好地方"
doc6 = "上海路和上海人"
doc7 = "喜欢小吃"
doc_test="我喜欢上海的小吃"

分词

首先,为了简化操作,把目标文档放到一个列表all_doc中。

all_doc = []
all_doc.append(doc0)
all_doc.append(doc1)
all_doc.append(doc2)
all_doc.append(doc3)
all_doc.append(doc4)
all_doc.append(doc5)
all_doc.append(doc6)
all_doc.append(doc7)

以下对目标文档进行分词,并且保存在列表all_doc_list中

all_doc_list = []
for doc in all_doc:
    doc_list = [word for word in jieba.cut(doc)]
    all_doc_list.append(doc_list)

把分词后形成的列表显示出来:

print(all_doc_list)

[[‘我’, ‘不’, ‘喜欢’, ‘上海’], [‘上海’, ‘是’, ‘一个’, ‘好’, ‘地方’], [‘北京’, ‘是’, ‘一个’, ‘好’, ‘地方’], [‘上海’, ‘好吃’, ‘的’, ‘在’, ‘哪里’], [‘上海’, ‘好玩’, ‘的’, ‘在’, ‘哪里’], [‘上海’, ‘是’, ‘好’, ‘地方’], [‘上海’, ‘路’, ‘和’, ‘上海’, ‘人’], [‘喜欢’, ‘小吃’]]

以下把测试文档也进行分词,并保存在列表doc_test_list中

doc_test_list = [word for word in jieba.cut(doc_test)]
doc_test_list

[‘我’, ‘喜欢’, ‘上海’, ‘的’, ‘小吃’]

制作语料库

首先用dictionary方法获取词袋(bag-of-words)

dictionary = corpora.Dictionary(all_doc_list)

词袋中用数字对所有词进行了编号

dictionary.keys()

[0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17]

编号与词之间的对应关系

dictionary.token2id

{‘一个’: 4, ‘上海’: 0, ‘不’: 1, ‘人’: 14, ‘北京’: 8, ‘和’: 15, ‘哪里’: 9, ‘喜欢’: 2, ‘在’: 10, ‘地方’: 5, ‘好’: 6, ‘好吃’: 11, ‘好玩’: 13, ‘小吃’: 17, ‘我’: 3, ‘是’: 7, ‘的’: 12, ‘路’: 16}

以下使用doc2bow制作语料库

corpus = [dictionary.doc2bow(doc) for doc in all_doc_list]

语料库如下。语料库是一组向量,向量中的元素是一个二元组(编号、频次数),对应分词后的文档中的每一个词。

[[(0, 1), (1, 1), (2, 1), (3, 1)], [(0, 1), (4, 1), (5, 1), (6, 1), (7, 1)], [(4, 1), (5, 1), (6, 1), (7, 1), (8, 1)], [(0, 1), (9, 1), (10, 1), (11, 1), (12, 1)], [(0, 1), (9, 1), (10, 1), (12, 1), (13, 1)], [(0, 1), (5, 1), (6, 1), (7, 1)], [(0, 2), (14, 1), (15, 1), (16, 1)], [(2, 1), (17, 1)]]

以下用同样的方法,把测试文档也转换为二元组的向量

doc_test_vec = dictionary.doc2bow(doc_test_list)
doc_test_vec

[(0, 1), (2, 1), (3, 1), (12, 1), (17, 1)]

相似度分析

使用TF-IDF模型对语料库建模

tfidf = models.TfidfModel(corpus)

获取测试文档中,每个词的TF-IDF值

tfidf[doc_test_vec]

[(0, 0.08112725037593049), (2, 0.3909393754390612), (3, 0.5864090631585919), (12, 0.3909393754390612), (17, 0.5864090631585919)]

对每个目标文档,分析测试文档的相似度

index = similarities.SparseMatrixSimilarity(tfidf[corpus], num_features=len(dictionary.keys()))
sim = index[tfidf[doc_test_vec]]
sim

array([ 0.54680777, 0.01055349, 0. , 0.17724207, 0.17724207, 0.01354522, 0.01279765, 0.70477605], dtype=float32)

根据相似度排序

sorted(enumerate(sim), key=lambda item: -item[1])

[(7, 0.70477605), (0, 0.54680777), (3, 0.17724207), (4, 0.17724207), (5, 0.013545224), (6, 0.01279765), (1, 0.010553493), (2, 0.0)]

从分析结果来看,测试文档与doc7相似度最高,其次是doc0,与doc2的相似度为零。大家可以根据TF-IDF的原理,看看是否符合预期。 最后总结一下文本相似度分析的步骤:

  1. 读取文档
  2. 对要计算的多篇文档进行分词
  3. 对文档进行整理成指定格式,方便后续进行计算
  4. 计算出词语的词频
  5. 【可选】对词频低的词语进行过滤
  6. 建立语料库词典
  7. 加载要对比的文档
  8. 将要对比的文档通过doc2bow转化为词袋模型
  9. 对词袋模型进行进一步处理,得到新语料库
  10. 将新语料库通过tfidfmodel进行处理,得到tfidf
  11. 通过token2id得到特征数 12、稀疏矩阵相似度,从而建立索引 13、得到最终相似度结果

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • python random 从集合中随机

    py3study
  • python文档

    #['BPF', 'LOG4', 'NV_MAGICCONST', 'RECIP_BPF', 'Random', 'SG_MAGICCONST', #'Syst...

    py3study
  • Python 列表 list 数组 ar

    Python中的列表(list)类似于C#中的可变数组(ArrayList),用于顺序存储结构。

    py3study
  • angular采用注释进行文档编写

    先加载 Dgeni 所需要的包依赖。下一步,需要通过配置来告知dgeni如何生成我们的文档。

    用户1437675
  • R语言进行中文分词,并对6W条微博聚类

    由于时间较紧,且人手不够,不能采用分类方法,主要是没有时间人工分类一部分生成训练集……所以只能用聚类方法,聚类最简单的方法无外乎:K-means与层次聚类。 尝...

    机器学习AI算法工程
  • Qt编写地图综合应用18-地图模式

    除了传统的街道图地图外,默认的一般都是街道图,还有卫星图、三维图等,其中又有叠加层,比如叠加路况图层和路网图层等,最近去了多家的地图官网看对应的api接口,总体...

    feiyangqingyun
  • ElasticSearch7.6.1 Kibana花样查询

    彼岸舞
  • 极限压缩 PNG

    2017-11-29 12:17

    walterlv
  • 使用tomcat方式实现websocket即时通讯服务端讲解

          <artifactId>javaee-api</artifactId>

    凯哥Java
  • ATT与ONF达成合作,推动网络的软件控制

    SDNLAB

扫码关注云+社区

领取腾讯云代金券