LSI和LDA模型初试验

从文本到向量

import csv

# 出于试验目的,只读取前5条评论
with open('comments.csv', 'r', newline='') as f:
    comments_reader = csv.reader(f, dialect='excel')
    corpus = [comment[1] for comment in comments_reader][1:6]

for i, comment in enumerate(corpus):
    print(i + 1, comment)
1 京东速度杠杠的!信任京东!昨晚11:30付的尾款!本来显示的是预计12号送达的!结果下午还是送来了!效率没得说!要的就是这速度!东西看着还不错吧!小巧玲珑的很好看!目前没发现什么问题!我个人觉得这屏幕分辨率太低了点!!不知道这个电子狗功能是不是鸡肋!看上的就是这个功能,希望好用!因为我原车本来就自带记录仪的!虽然还没有上车使用!但因为信任京东,信任360就先好评了!具体表现要明天使用后才知道!后续再补充!
2 喜欢这款行车记录仪,大家认真看看评价吧,差不多花了不到一半的价格买到它的,卫︿新,去∧艘~东家羊毛~你懂得哦,这个宫宗皓可以享半价哦!多少年了一直买京东,从来不知道还有补贴,不过知道它的人不多,经常省个百八十不成问题,不光这一个,所有商品基本都有。商家发货快,问了客服很多问题,照着提示已经安装好了,安装也方便,装上去也不占地方,很上档次,中间遇上了一点小麻烦,咨询了客服,态度不错很快就帮我解决了,今天开出去溜了一下,看起来也很上档次,图像拍摄的很清晰,正品,效果非常棒了,但是基本能满足,也对得起这个价格。物有所值,买到合心意质量好的东东,质量好杠杠滴,赞一个!而且价格超级划算,我就是关住了 ~ 东 家 羊 毛 ~,这个威威宫宗号。半价买的,排在第一个才是哦。一如既往的支持京东。
3 生产日期很美丽!2017-11,东西还没用上去,但是从体积上肯定不错,毕竟不会被遮挡。隐藏的很好,而且参数我看过,和后视镜版本M302几乎一样,胜在不占空间。东西也比较简约,使用过一段日子再来评价。外观还不错!
4 这是我精挑细选的一款记录仪,不用支架,小巧玲珑,携带方便,摄像高清,还可以无线联网,非常棒
5 看个一分钟录像,卡了一个小时,下载四五次,还下不下来,真**上火,APP也卸载了重新安装,行车记录仪也恢复出厂设置,鼓捣一晚上还是这样,气死我了
# 分别对各文本进行预处理,流程为:1、分词,2、去除只在整个语料库中出现1次的词,
# 3、去除停用词

# 分词
import jieba

texts = [[w for w in jieba.cut(text)] for text in corpus]

# 去除停用词
with open('stoplist_ch.txt', 'r', encoding='utf-8') as f:
    stoplist = [w.rstrip('\n') for w in f.readlines()]
texts = [[w for w in text if w not in stoplist]
         for text in texts]

# 去除只在整个语料库中出现1次的词
fdist = {}
for text in texts:
    for w in text:
        fdist[w] = fdist.get(w, 0) + 1

texts = [[w for w in text if fdist[w] > 1]
         for text in texts]

print(texts)
[['京东', '速度', '杠杠', '信任', '京东', '11', '本来', '速度', '东西', '不错', '小巧玲珑', '问题', '知道', '功能', '功能', '本来', '记录仪', '使用', '信任', '京东', '信任', '使用', '知道', '再'], ['行车', '记录仪', '评价', '价格', '买到', '半价', '买', '京东', '知道', '知道', '一个', '客服', '问题', '安装', '好', '安装', '占', '上档次', '客服', '不错', '上档次', '棒', '价格', '买到', '质量', '好', '质量', '好', '杠杠', '一个', '价格', '半价', '买', '京东'], ['11', '东西', '不错', '好', '占', '东西', '使用', '再', '评价', '不错'], ['记录仪', '小巧玲珑', '棒'], ['一个', '行车', '记录仪']]
# 将这些词编号,以词典键值对的方式表示
from gensim import corpora

dictionary = corpora.Dictionary(texts)
print(dictionary)
Dictionary(29 unique tokens: ['11', '不错', '东西', '京东', '使用']...)
# 以"词:编号"的方式shi显示
print(dictionary.token2id)
{'11': 0, '不错': 1, '东西': 2, '京东': 3, '使用': 4, '信任': 5, '再': 6, '功能': 7, '小巧玲珑': 8, '本来': 9, '杠杠': 10, '知道': 11, '记录仪': 12, '速度': 13, '问题': 14, '一个': 15, '上档次': 16, '买': 17, '买到': 18, '价格': 19, '半价': 20, '占': 21, '好': 22, '安装': 23, '客服': 24, '棒': 25, '行车': 26, '评价': 27, '质量': 28}
# 用词袋的方法将各词在各文本的出现次数,即词频表示出来
corpus_mm = [dictionary.doc2bow(text) for text in texts]
print(corpus_mm)
[[(0, 1), (1, 1), (2, 1), (3, 3), (4, 2), (5, 3), (6, 1), (7, 2), (8, 1), (9, 2), (10, 1), (11, 2), (12, 1), (13, 2), (14, 1)], [(1, 1), (3, 2), (10, 1), (11, 2), (12, 1), (14, 1), (15, 2), (16, 2), (17, 2), (18, 2), (19, 3), (20, 2), (21, 1), (22, 3), (23, 2), (24, 2), (25, 1), (26, 1), (27, 1), (28, 2)], [(0, 1), (1, 2), (2, 2), (4, 1), (6, 1), (21, 1), (22, 1), (27, 1)], [(8, 1), (12, 1), (25, 1)], [(12, 1), (15, 1), (26, 1)]]

这样一来,语料库中各文本就表示成了文本中各词的出现次数了,比如,第1个文本的词向量即为:1, 1, 1, 3, 2, 3, 1, 2, 1, 2, 1, 2, 1, 2, 1。值得注意的是,没有出现的词不会在打印中表示。

向量转换

上述步骤得到的是以词频作为向量各纬度的值,但并没有表现出词与词之间的关系,这是词袋的不足之一。

因此,在词袋向量的基础上,应进一步提取更多信息。为了达到这个目的,可以将向量各纬度的值转换成另外一种值。比如下面介绍的TF-IDF。

# 转换初始化,指定要转换为TF-IDF向量
import gensim

tfidf_trans = gensim.models.TfidfModel(corpus_mm)
# 转换为TF-IDF向量
corpus_tfidf = tfidf_trans[corpus_mm]
for doc in corpus_tfidf:
    print(doc)
[(0, 0.10650413173766084), (1, 0.05937530265887042), (2, 0.10650413173766084), (3, 0.31951239521298247), (4, 0.21300826347532167), (5, 0.5612141915880775), (6, 0.10650413173766084), (7, 0.3741427943920516), (8, 0.10650413173766084), (9, 0.3741427943920516), (10, 0.10650413173766084), (11, 0.21300826347532167), (12, 0.025936866279295836), (13, 0.3741427943920516), (14, 0.10650413173766084)]
[(1, 0.04686268994890363), (3, 0.1681193991574051), (10, 0.08405969957870255), (11, 0.1681193991574051), (12, 0.020470991612052493), (14, 0.08405969957870255), (15, 0.1681193991574051), (16, 0.29529681509070516), (17, 0.29529681509070516), (18, 0.29529681509070516), (19, 0.4429452226360578), (20, 0.29529681509070516), (21, 0.08405969957870255), (22, 0.2521790987361076), (23, 0.29529681509070516), (24, 0.29529681509070516), (25, 0.08405969957870255), (26, 0.08405969957870255), (27, 0.08405969957870255), (28, 0.29529681509070516)]
[(0, 0.29823262853716886), (1, 0.3325251761267265), (2, 0.5964652570743377), (4, 0.29823262853716886), (6, 0.29823262853716886), (21, 0.29823262853716886), (22, 0.29823262853716886), (27, 0.29823262853716886)]
[(8, 0.6968503263117378), (12, 0.1697034043219193), (25, 0.6968503263117378)]
[(12, 0.1697034043219193), (15, 0.6968503263117378), (26, 0.6968503263117378)]
# 更进一步,探究各文本在语义上倾向于哪个主题
# 先划分主题,使用LSI模型
lsi_trans = gensim.models.LsiModel(corpus_tfidf, id2word=dictionary,
                                   num_topics=4) # 转换初始化,指定划分4个主题
corpus_lsi = lsi_trans[corpus_tfidf] # 词袋->TF-IDF->LSI
# 看看各个主题都有什么主题词
lsi_trans.print_topics(4)
[(0,
  '0.315*"东西" + 0.258*"一个" + 0.254*"信任" + 0.253*"好" + 0.230*"使用" + 0.224*"京东" + 0.218*"行车" + 0.210*"价格" + 0.198*"不错" + 0.187*"小巧玲珑"'),
 (1,
  '0.537*"一个" + 0.509*"行车" + -0.281*"东西" + -0.222*"信任" + -0.204*"使用" + -0.162*"11" + -0.162*"再" + 0.149*"价格" + -0.148*"速度" + -0.148*"功能"'),
 (2,
  '0.662*"小巧玲珑" + 0.638*"棒" + -0.150*"东西" + -0.144*"一个" + -0.131*"行车" + 0.129*"记录仪" + -0.118*"好" + -0.093*"评价" + -0.093*"占" + -0.091*"不错"'),
 (3,
  '-0.387*"信任" + -0.329*"行车" + -0.278*"一个" + 0.268*"价格" + -0.258*"速度" + -0.258*"本来" + -0.258*"功能" + 0.241*"好" + 0.179*"质量" + 0.179*"安装"')]
# 看看各文本在各主题上的分布
for doc in corpus_lsi:
    print(doc)
[(0, 0.6151990923970965), (1, -0.43114870816315265), (2, 0.10554078138694145), (3, -0.5507585471447924)]
[(0, 0.6452603721867233), (1, 0.36676022694119653), (2, -0.14588731937618363), (3, 0.48322823901839956)]
[(0, 0.6091519197175418), (1, -0.43608218559430395), (2, -0.2693719615275453), (3, 0.23616797769920406)]
[(0, 0.2721984576989459), (1, 0.11753367175861239), (2, 0.9274598337066065), (3, 0.12780692177247774)]
[(0, 0.34886155667911756), (1, 0.7516857754005692), (2, -0.16957436157580397), (3, -0.43465064036045764)]

可以看出,从语义上说,第1、2、3个文本偏向第1个主题,第4个文本偏向第3个主题,第5个文本偏向第2个主题。

LDA模型

上面的LSI模型得到的可以看作是"语义向量",可用于计算文本之间的相似性,而LDA模型则侧重于计算某个主题所对应词在该主题下的权重,也可以看作是某主题下词的概率分布。

# LDA模型由词袋向量转换而来
lda_trans = gensim.models.LdaModel(corpus_mm, id2word=dictionary,
                                   num_topics=4) # 转换初始化,指定划分4个主题
corpus_lda = lda_trans[corpus_mm] # 词袋->LDA
# 看看各主题都有什么主题词
lda_trans.print_topics(4)
[(0,
  '0.092*"京东" + 0.072*"知道" + 0.050*"信任" + 0.047*"好" + 0.041*"价格" + 0.038*"功能" + 0.037*"速度" + 0.037*"不错" + 0.036*"使用" + 0.036*"杠杠"'),
 (1,
  '0.055*"信任" + 0.053*"本来" + 0.052*"使用" + 0.051*"京东" + 0.043*"功能" + 0.043*"速度" + 0.042*"知道" + 0.038*"记录仪" + 0.037*"小巧玲珑" + 0.037*"问题"'),
 (2,
  '0.069*"信任" + 0.060*"不错" + 0.060*"使用" + 0.054*"东西" + 0.049*"本来" + 0.048*"速度" + 0.045*"功能" + 0.044*"知道" + 0.043*"京东" + 0.043*"再"'),
 (3,
  '0.075*"记录仪" + 0.061*"不错" + 0.060*"一个" + 0.060*"好" + 0.052*"东西" + 0.048*"价格" + 0.047*"评价" + 0.046*"棒" + 0.045*"行车" + 0.040*"质量"')]
# 看看各文本在各主题上的分布
for doc in corpus_lda:
    print(doc)
[(0, 0.9686841), (1, 0.010232531), (2, 0.0106450515), (3, 0.0104383305)]
[(0, 0.42112163), (3, 0.56442404)]
[(0, 0.02371528), (1, 0.023032475), (2, 0.02412851), (3, 0.92912376)]
[(0, 0.06447045), (1, 0.06305108), (2, 0.06310642), (3, 0.809372)]
[(0, 0.06418085), (1, 0.06276632), (2, 0.06285436), (3, 0.8101985)]

计算相似性

# TODO: 现在有一个新文本,需要分析与其相似的文本有哪些

原文地址:https://www.cnblogs.com/tspeaking/p/10850408.html

时间: 2024-10-11 11:43:16

LSI和LDA模型初试验的相关文章

C++ 类的对象管理模型初讲

//类的对象管理模型初讲 #include<iostream> using namespace std; class PointA{ private: int x;//占据4个字节大小的内存空间 int y;//占据4个字节大小的内存空间 int z;//占据4个字节大小的内存空间 };//总共占据12个字节 class PointB{ public: PointB(int _x, int _y,int _z){ x = _x; y = _y; z = _z; } void GetX(){ c

lda模型的python实现

LDA(Latent Dirichlet Allocation)是一种文档主题生成模型,最近看了点资料,准备使用python实现一下.至于数学模型相关知识,某度一大堆,这里也给出之前参考过的一个挺详细的文档lda算法漫游指南 这篇博文只讲算法的sampling方法python实现. 完整实现项目开源python-LDA lda模型变量申请及初始化 # #伪代码 # 输入:文章集合(分词处理后),K(类的个数) 输出:已经随机分派了一次的lda模型 begin 申请几个统计量: p 概率向量 维度

Python:电商产品评论数据情感分析,jieba分词,LDA模型

本节涉及自然语言处理(NLP),具体涉及文本数据采集.预处理.分词.去停用词.词频分析.LDA主题模型 代码部分 1 # -*- coding: utf-8 -*- 2 """ 3 Created on Mon Oct 1 12:13:11 2018 4 5 @author: Luove 6 """ 7 8 import os 9 import pandas as pd 10 import jieba 11 from gensim import

计算LDA模型困惑度

http://www.52nlp.cn/lda-math-lda-%E6%96%87%E6%9C%AC%E5%BB%BA%E6%A8%A1 LDA主题模型评估方法--Perplexity http://www.52nlp.cn/lda-math-lda-%E6%96%87%E6%9C%AC%E5%BB%BA%E6%A8%A1 LDA-math-LDA 文本建模 http://www.iyunv.com/thread-59890-1-1.html 用python计算lda语言模型的困惑度并作图 h

动手实践用LDA模型计算两篇英文文档相似度

知道原理的同学这部分可以略过直接看实践部分 什么是TD-IDF? 构造文档模型 我们这里使用空间向量模型来数据化文档内容:向量空间模型中将文档表达为一个矢量. 用特征向量(T1,W1:T2,W2:T3, W3:…:Tn,Wn)表示文档. Ti是词条项,Wi是Ti在文档中的重要程度, 即将文档看作是由一组相互独立的词条组构成,把T1,T2 …,Tn看成一个n 维坐标系中的坐标轴,对于每一词条,根据其重要程度赋以一定的权值Wi,作为对应坐标轴的坐标值. 权重Wi用词频表示,词频分为绝对词频和相对词频

边练边学--plist文件,懒加载,模型初使用--补充instancetype

一.什么是plist文件 1>将数据直接写在代码里面,不是一种合理的做法.如果数据经常修改,就要经常翻开对应的代码进行修改,造成代码扩展性低 2>因此,可以考虑将经常变得数据放在文件中进行存储,程序启动后从文件中读取最新的数据.如果要变动数据,直接修改数据文件即可,不用修改代码 3>一般可以使用属性列表文件存储NSArray或者NSDictionary之类的数据,这种“属性列表文件”的扩展名是plist,因此也成为“plist文件” 二.创建plist文件 三.解析plist文件 代码实

DataFrame编程模型初谈与Spark SQL

Spark SQL在Spark内核基础上提供了对结构化数据的处理,在Spark1.3版本中,Spark SQL不仅可以作为分布式的SQL查询引擎,还引入了新的DataFrame编程模型. 在Spark1.3版本中,Spark SQL不再是Alpha版本,除了提供更好的SQL标准兼容之外,还引进了新的组件DataFrame.同时,Spark SQL数据源API也实现了与新组件DataFrame的交互,允许用户直接通过Hive表.Parquet文件以及一些其他数据源生成DataFrame.用户可以在

Maximum Entropy Model(最大熵模型)初理解

1,简单概率知识理解 1.1 随机变量(random variable) 表示随机现象(在一定条件下,并不总是出现相同结果的现象称为随机现象)各种结果的实值函数(一切可能的样本点).如掷一颗骰子,它的所有可能结果是出现1点.2点.3点.4点.5点和6点 ,若定义X为掷一颗骰子时出现的点数,则X为一随机变量.随机变量   X∈{1,2,3,4,5,6}.

我爱自然语言处理[转]

最近试了一下Word2Vec, GloVe 以及对应的python版本 gensim word2vec 和 python-glove,就有心在一个更大规模的语料上测试一下,自然而然维基百科的语料进入了视线.维基百科官方提供了一个很好的维基百科数据源:https://dumps.wikimedia.org,可以方便的下载多种语言多种格式的维基百科数据.此前通过gensim的玩过英文的维基百科语料并训练LSI,LDA模型来计算两个文档的相似度,所以想看看gensim有没有提供一种简便的方式来处理维基