Python_LDA实现方法详解


Posted in Python onOctober 25, 2017

LDA(Latent Dirichlet allocation)模型是一种常用而用途广泛地概率主题模型。其实现一般通过Variational inference和Gibbs Samping实现。作者在提出LDA模型时给出了其变分推理的C源码(后续贴出C++改编的类),这里贴出基于Python的第三方模块改写的LDA类及实现。

#coding:utf-8
import numpy as np
import lda
import lda.datasets
import jieba
import codecs
class LDA_v20161130():
  def __init__(self, topics=2):
    self.n_topic = topics
    self.corpus = None
    self.vocab = None
    self.ppCountMatrix = None
    self.stop_words = [u',', u'。', u'、', u'(', u')', u'·', u'!', u' ', u':', u'“', u'”', u'\n']
    self.model = None
  def loadCorpusFromFile(self, fn):
    # 中文分词
    f = open(fn, 'r')
    text = f.readlines()
    text = r' '.join(text)
    seg_generator = jieba.cut(text)
    seg_list = [i for i in seg_generator if i not in self.stop_words]
    seg_list = r' '.join(seg_list)
    # 切割统计所有出现的词纳入词典
    seglist = seg_list.split(" ")
    self.vocab = []
    for word in seglist:
      if (word != u' ' and word not in self.vocab):
        self.vocab.append(word)
    CountMatrix = []
    f.seek(0, 0)
    # 统计每个文档中出现的词频
    for line in f:
      # 置零
      count = np.zeros(len(self.vocab),dtype=np.int)
      text = line.strip()
      # 但还是要先分词
      seg_generator = jieba.cut(text)
      seg_list = [i for i in seg_generator if i not in self.stop_words]
      seg_list = r' '.join(seg_list)
      seglist = seg_list.split(" ")
      # 查询词典中的词出现的词频
      for word in seglist:
        if word in self.vocab:
          count[self.vocab.index(word)] += 1
      CountMatrix.append(count)
    f.close()
    #self.ppCountMatrix = (len(CountMatrix), len(self.vocab))
    self.ppCountMatrix = np.array(CountMatrix)
    print "load corpus from %s success!"%fn
  def setStopWords(self, word_list):
    self.stop_words = word_list
  def fitModel(self, n_iter = 1500, _alpha = 0.1, _eta = 0.01):
    self.model = lda.LDA(n_topics=self.n_topic, n_iter=n_iter, alpha=_alpha, eta= _eta, random_state= 1)
    self.model.fit(self.ppCountMatrix)
  def printTopic_Word(self, n_top_word = 8):
    for i, topic_dist in enumerate(self.model.topic_word_):
      topic_words = np.array(self.vocab)[np.argsort(topic_dist)][:-(n_top_word + 1):-1]
      print "Topic:",i,"\t",
      for word in topic_words:
        print word,
      print
  def printDoc_Topic(self):
    for i in range(len(self.ppCountMatrix)):
      print ("Doc %d:((top topic:%s) topic distribution:%s)"%(i, self.model.doc_topic_[i].argmax(),self.model.doc_topic_[i]))
  def printVocabulary(self):
    print "vocabulary:"
    for word in self.vocab:
      print word,
    print
  def saveVocabulary(self, fn):
    f = codecs.open(fn, 'w', 'utf-8')
    for word in self.vocab:
      f.write("%s\n"%word)
    f.close()
  def saveTopic_Words(self, fn, n_top_word = -1):
    if n_top_word==-1:
      n_top_word = len(self.vocab)
    f = codecs.open(fn, 'w', 'utf-8')
    for i, topic_dist in enumerate(self.model.topic_word_):
      topic_words = np.array(self.vocab)[np.argsort(topic_dist)][:-(n_top_word + 1):-1]
      f.write( "Topic:%d\t"%i)
      for word in topic_words:
        f.write("%s "%word)
      f.write("\n")
    f.close()
  def saveDoc_Topic(self, fn):
    f = codecs.open(fn, 'w', 'utf-8')
    for i in range(len(self.ppCountMatrix)):
      f.write("Doc %d:((top topic:%s) topic distribution:%s)\n" % (i, self.model.doc_topic_[i].argmax(), self.model.doc_topic_[i]))
    f.close()

算法实现demo:

例如,抓取BBC川普当选的新闻作为语料,输入以下代码:

if __name__=="__main__":
  _lda = LDA_v20161130(topics=20)
  stop = [u'!', u'@', u'#', u',',u'.',u'/',u';',u' ',u'[',u']',u'$',u'%',u'^',u'&',u'*',u'(',u')',
      u'"',u':',u'<',u'>',u'?',u'{',u'}',u'=',u'+',u'_',u'-',u'''''']
  _lda.setStopWords(stop)
  _lda.loadCorpusFromFile(u'C:\\Users\Administrator\Desktop\\BBC.txt')
  _lda.fitModel(n_iter=1500)
  _lda.printTopic_Word(n_top_word=10)
  _lda.printDoc_Topic()
  _lda.saveVocabulary(u'C:\\Users\Administrator\Desktop\\vocab.txt')
  _lda.saveTopic_Words(u'C:\\Users\Administrator\Desktop\\topic_word.txt')
  _lda.saveDoc_Topic(u'C:\\Users\Administrator\Desktop\\doc_topic.txt')

因为语料全部为英文,因此这里的stop_words全部设置为英文符号,主题设置20个,迭代1500次。结果显示,文档148篇,词典1347词,总词数4174,在i3的电脑上运行17s。
Topic_words部分输出如下:

Topic: 0
to will and of he be trumps the what policy
Topic: 1 he would in said not no with mr this but
Topic: 2 for or can some whether have change health obamacare insurance
Topic: 3 the to that president as of us also first all
Topic: 4 trump to when with now were republican mr office presidential
Topic: 5 the his trump from uk who president to american house
Topic: 6 a to that was it by issue vote while marriage
Topic: 7 the to of an are they which by could from
Topic: 8 of the states one votes planned won two new clinton
Topic: 9 in us a use for obama law entry new interview
Topic: 10 and on immigration has that there website vetting action given

Doc_Topic部分输出如下:

Doc 0:((top topic:4) topic distribution:[ 0.02972973 0.0027027 0.0027027 0.16486486 0.32702703 0.19189189
0.0027027 0.0027027 0.02972973 0.0027027 0.02972973 0.0027027
0.0027027 0.0027027 0.02972973 0.0027027 0.02972973 0.0027027
0.13783784 0.0027027 ])
Doc 1:((top topic:18) topic distribution:[ 0.21 0.01 0.01 0.01 0.01 0.01 0.01 0.01 0.11 0.01 0.01 0.01
0.01 0.01 0.01 0.01 0.01 0.01 0.31 0.21])
Doc 2:((top topic:18) topic distribution:[ 0.02075472 0.00188679 0.03962264 0.00188679 0.00188679 0.00188679
0.00188679 0.15283019 0.00188679 0.02075472 0.00188679 0.24716981
0.00188679 0.07735849 0.00188679 0.00188679 0.00188679 0.00188679
0.41698113 0.00188679])

当然,对于英文语料,需要排除大部分的虚词以及常用无意义词,例如it, this, there, that...在实际操作中,需要合理地设置参数。

换中文语料尝试,采用习大大就卡斯特罗逝世发表的吊唁文章和朴槿惠辞职的新闻。

Topic: 0
的 同志 和 人民 卡斯特罗 菲德尔 古巴 他 了 我
Topic: 1 在 朴槿惠 向 表示 总统 对 将 的 月 国民
Doc 0:((top topic:0) topic distribution:[ 0.91714123 0.08285877])
Doc 1:((top topic:1) topic distribution:[ 0.09200666 0.90799334])

还是存在一些虚词,例如“的”,“和”,“了”,“对”等词的干扰,但是大致来说,两则新闻的主题分布很明显,效果还不赖。

总结

以上就是本文关于Python_LDA实现方法详解的全部内容,希望对大家有所帮助。感兴趣的朋友可以继续参阅本站:python+mongodb数据抓取详细介绍、Python探索之创建二叉树、Python探索之修改Python搜索路径等,有什么问题可以随时留言,欢迎大家一起交流讨论。感谢朋友们对本站的支持!

Python 相关文章推荐
Python爬虫实战:分析《战狼2》豆瓣影评
Mar 26 Python
python将处理好的图像保存到指定目录下的方法
Jan 10 Python
python+selenium 定位到元素,无法点击的解决方法
Jan 30 Python
利用Python+阿里云实现DDNS动态域名解析的方法
Apr 01 Python
python中bytes和str类型的区别
Oct 21 Python
wxPython绘图模块wxPyPlot实现数据可视化
Nov 19 Python
centos7中安装python3.6.4的教程
Dec 11 Python
pytorch实现线性拟合方式
Jan 15 Python
Django静态文件加载失败解决方案
Aug 26 Python
python自动化发送邮件实例讲解
Jan 04 Python
pytorch 实现L2和L1正则化regularization的操作
Mar 03 Python
python编程简单几行代码实现视频转换Gif示例
Oct 05 Python
python+mongodb数据抓取详细介绍
Oct 25 #Python
python装饰器实例大详解
Oct 25 #Python
Python3 模块、包调用&amp;路径详解
Oct 25 #Python
Python探索之创建二叉树
Oct 25 #Python
Python探索之修改Python搜索路径
Oct 25 #Python
python中 logging的使用详解
Oct 25 #Python
python下载文件记录黑名单的实现代码
Oct 24 #Python
You might like
可以保证单词完整性的PHP英文字符串截取代码分享
2014/07/15 PHP
PHP+Ajax+JS实现多图上传
2016/05/07 PHP
PHP常用排序算法实例小结【基本排序,冒泡排序,快速排序,插入排序】
2017/02/07 PHP
thinkPHP3.2.3实现阿里大于短信验证的方法
2018/06/06 PHP
PHP连接sftp并下载文件的方法教程
2018/08/26 PHP
asp.net下利用js实现返回上一页的实现方法小集
2009/11/24 Javascript
解析瀑布流布局:JS+绝对定位的实现
2013/05/08 Javascript
动态创建script在IE中缓存js文件时导致编码的解决方法
2014/05/04 Javascript
js如何判断访问是来自搜索引擎(蜘蛛人)还是直接访问
2015/09/14 Javascript
easyui window refresh 刷新两次的解决方法(推荐)
2016/05/18 Javascript
Javascript实现图片不间断滚动的代码
2016/06/22 Javascript
详解js的事件代理(委托)
2016/12/22 Javascript
微信小程序 解决swiper不显示图片的方法
2017/01/04 Javascript
jquery 正整数数字校验正则表达式
2017/01/10 Javascript
JavaScript中三种常见的排序方法
2017/02/24 Javascript
利用Angular7开发一个Radio组件的全过程
2019/07/11 Javascript
详解JavaScript修改注册表的方法
2020/01/05 Javascript
JS实现transform实现扇子效果
2020/01/17 Javascript
js中forEach,for in,for of循环的用法示例小结
2020/03/14 Javascript
从0到1学习JavaScript编写贪吃蛇游戏
2020/07/28 Javascript
[05:31]DOTA2英雄梦之声_第04期_光之守卫
2014/06/23 DOTA
用实例详解Python中的Django框架中prefetch_related()函数对数据库查询的优化
2015/04/01 Python
进一步理解Python中的函数编程
2015/04/13 Python
Python 多进程和数据传递的理解
2017/10/09 Python
使用python实现链表操作
2018/01/26 Python
python爬虫 urllib模块反爬虫机制UA详解
2019/08/20 Python
解决django的template中如果无法引用MEDIA_URL问题
2020/04/07 Python
python按顺序重命名文件并分类转移到各个文件夹中的实现代码
2020/07/21 Python
matplotlib制作雷达图报错ValueError的实现
2021/01/05 Python
JBL澳大利亚官方商店:扬声器、耳机和音响系统
2018/05/24 全球购物
普师专业个人自荐信范文
2013/11/26 职场文书
大学生职业规划论文
2014/01/11 职场文书
司仪主持词两篇
2014/03/22 职场文书
2014四风问题对照检查材料范文
2014/09/15 职场文书
Python数据清洗工具之Numpy的基本操作
2021/04/22 Python
java executor包参数处理功能 
2022/02/15 Java/Android