解释Spark MLLib LDA结果

时间:2015-10-25 14:17:40

标签: apache-spark lda apache-spark-mllib

我在一组文件的火花上运行LDA并观察到topicMatrix的值,它代表了术语的主题分布,大于1,如548.2201,685.2436,138.4013 ......这些值是什么意思?这些是分布的对数值还是其他东西。如何将这些值转换为概率分布值。 提前致谢。

2 个答案:

答案 0 :(得分:4)

在两个模型中(即DistributedLDAModelLocalLDAMoel)我相信topicsMatrix方法会返回(大约有一些正则化,因为Dirichlet先于主题)预期的单词主题计数矩阵。要检查这一点,您可以使用该矩阵并总结所有列。生成的向量(长度为topic-count-size)应该大致等于单词count(在所有文档上)。在任何情况下,要获得主题(词典中单词的概率分布),您需要规范化列由topicsMatrix返回的矩阵,以便每个总和为1。

我还没有完全测试过,但是这样的事情应该能够规范化topicsMatrix返回的矩阵的列:

import breeze.linalg.{DenseVector => BDV}
import org.apache.spark.mllib.linalg._

def normalizeColumns(m: Matrix): DenseMatrix = {
  val bm = Matrices.toBreeze(m).toDenseMatrix
  val columnSums = BDV.zeros[Double](bm.cols).t
  var i = bm.rows
  while (i > 0) { i -= 1; columnSums += bm(i, ::) }
  i = bm.cols
  while (i > 0) { i -= 1; bm(::, i) /= columnSums(i) }
  new DenseMatrix(bm.rows, bm.cols, bm.data)
} 

答案 1 :(得分:0)

规范化纯scala

中的topicsMatrix返回的矩阵的列
def formatSparkLDAWordOutput(wordTopMat: Matrix, wordMap: Map[Int, String]): scala.Predef.Map[String, Array[Double]] = {

// incoming word top matrix is in column-major order and the columns are unnormalized
val m = wordTopMat.numRows
val n = wordTopMat.numCols
val columnSums: Array[Double] = Range(0, n).map(j => (Range(0, m).map(i => wordTopMat(i, j)).sum)).toArray

val wordProbs: Seq[Array[Double]] = wordTopMat.transpose.toArray.grouped(n).toSeq
  .map(unnormProbs => unnormProbs.zipWithIndex.map({ case (u, j) => u / columnSums(j) }))

wordProbs.zipWithIndex.map({ case (topicProbs, wordInd) => (wordMap(wordInd), topicProbs) }).toMap

}

https://github.com/apache/incubator-spot/blob/v1.0-incubating/spot-ml/src/main/scala/org/apache/spot/lda/SpotLDAWrapper.scala#L237