(Ich werde einen Artikel veröffentlichen, den ich vor einem Jahr vergessen habe, für den Entwurf der Verdauung zu veröffentlichen.)
Ich habe einige der LDA-Implementierungen zum Vergleich angesprochen. Es scheint, dass die Optionen wie folgt sind, aber ich werde das Verfahren zum Ausführen der LDA jeder Sprache, die in einem Memo geschrieben ist, zusammenfassen.
Verwendete Sprache | Nutzungsmuster | Erweiterbarkeit laden | Algorithmus | |
---|---|---|---|---|
Spark MLlib 1.6.0 | Scala,Java, Python,R |
Bibliothek | Parallel/Verteilt | Variante Bayes, EM |
gensim | Python | Bibliothek | Parallel | Variante Bayes |
GibbsLDA++ | Schale | Befehl | - | Gibbs Sampling |
R | R | Bibliothek | - | Gibbs Sampling |
Jedes wird ausgeführt und die Zeit wird gemessen, aber die Ausführungsbedingungen sind sehr unterschiedlich, wie unten gezeigt. Bitte lesen Sie es ohne Missverständnisse.
Wird unter den Bedingungen von $ k = 100 $ und $ iter = 50 $ für $ 13.033 $ ausgeführt. Dokument $ 20.780 $ Wörter, die durch Durchführen einer morphologischen Analyse und Entfernen unnötiger morphologischer Elemente erhalten wurden.
Spark MLlib
Algorithmus | Nodes | Cores | Ausführungszeit |
---|---|---|---|
EM | 5 | 80 | 224.092 |
EM | 1 | 8 | 81.854 |
EM | 1 | 1 | 112.606 |
Variante Bayes | 1 | 8 | 220.147 |
Variante Bayes | 1 | 1 | 310.367 |
Die Ausführungszeit ist langsamer als bei anderen, da RDD auch die lokale Datei liest und die BoW erstellt. Die langsamsten Ergebnisse der verteilten Ausführung sind wahrscheinlich auf die höheren Kosten für das Mischen und die Datenübertragung zwischen Knoten zurückzuführen als die LDA-Berechnungskosten selbst.
gensim
Algorithmus | Nodes | Cores | Ausführungszeit |
---|---|---|---|
Variante Bayes | 1 | 4 | 15.396 |
Variante Bayes | 1 | 1 | 20.576 |
Pythons Gensim scheint nur eine Variante von Bayes zu sein, aber es scheint ein gutes Leistungsgleichgewicht mit mehr Arbeitern, paralleler Verarbeitung und hoher Geschwindigkeit zu haben.
GibbsLDA++
Algorithmus | Nodes | Cores | Ausführungszeit |
---|---|---|---|
Gibbs Sampling | 1 | 1 | 58.993 |
Es war schneller als Gensim in der Nähe von $ k = 10 $ mit Eingabe / Ausgabe-Verarbeitung von lokalen Dateien zusätzlich zu einem einzelnen Thread, aber ist es langsamer, wenn $ k $ größer wird? Der Maßstab mag schwierig sein, aber ist er für eine kleine Ad-hoc-Ausführung geeignet?
Algorithmus | Nodes | Cores | Ausführungszeit |
---|---|---|---|
Collapsed Gibbs Sampling | 1 | 1 | 24.247 |
Die Berechnung selbst war überraschend schneller als "lda.collapsed.gibbs.sampler {lda}" von GibbsLDA ++ R (Das Lesen und Konvertieren einer lokalen Datei in ein Format, das an die Bibliothek übergeben werden kann, war jedoch langsam, sodass sie insgesamt langsam ist). R ist schneller als die praktische Geschwindigkeit lda {lda}
und [lda.cvb0 {lda}
](http Es ist ein guter Eindruck, viele Implementierungen und Algorithmen zu erwarten (z. B. //www.inside-r.org/packages/cran/lda/docs/lda.cvb0).
gensim
# -*- coding: utf-8 -*-
#LDA-Beispiel von Python Gensim
from gensim import corpora, models
import time
#Dokumentdaten lesen(Morphologische Analyse/Eine Textdatei, in der Wörter in einem zeilenweisen Dokument mit extrahierter Nomenklatur durch Leerzeichen getrennt sind.)
texts = [ ]
for line in open('docs.gibbs', 'r'):
texts.append(line.split())
#Wörterbuch erstellen(id:Wort:Anzahl der Auftritte)
dictionary = corpora.Dictionary(texts)
dictionary.save_as_text('./docs.dic')
# dictionary = corpora.Dictionary.load_from_text("./docs.dic")
#Korpuserstellung
corpus = [dictionary.doc2bow(text) for text in texts]
corpora.MmCorpus.serialize('corpus.mm', corpus)
# corpus = corpora.MmCorpus('corpus.mm')
#LDA-Berechnung
t0 = int(time.time() * 1000)
lda = models.ldamodel.LdaModel(corpus, num_topics=100, iterations=50)
t1 = int(time.time() * 1000)
print t1 - t0
#LDA-Berechnung(Multiprozessor-kompatible Version)
t0 = int(time.time() * 1000)
lda = models.ldamulticore.LdaMulticore(corpus, num_topics=10, iterations=50, workers=4)
t1 = int(time.time() * 1000)
print t1 - t0
GibbsLDA++
GibbsLDA ++ und sein Java-Port von JGibbsLDA sind Befehlszeilen-LDA-Implementierungen. Ich habe Gibbs Sampling implementiert, aber es scheint keine parallele Verarbeitung (Multi-Core-Unterstützung) oder verteilte Verarbeitung zu unterstützen.
Laden Sie GibbsLDA ++ - 0.2.tar.gz
von GibbsLDA ++: A C / C ++ Gibbs Sampling LDA herunter, entpacken und erstellen Sie es.
$ tar zxvf GibbsLDA++-0.2.tar.gz
$ cd GibbsLDA++-0.2/
$ make all
Wenn "g ++" verfügbar ist, wird "make all" den Build abschließen und der Befehl "src / lda" wird ausgeführt.
Wenn "Fehler:" atof "in diesem Bereich nicht deklariert wurde", tritt "hier:" printf "nicht in diesem Bereich auf" (http://yuutookun.hatenablog.com/entry/20120831/) 2 Fügen Sie der Datei, die sich auf 1346394002 bezieht, # include
hinzu.
$ vim src/util.cpp
...
#include <stdio.h>
#include <stdlib.h> //hinzufügen
#include <string>
...
$ vim src/lda.cpp
...
*/
#include <stdio.h> //hinzufügen
#include "model.h"
...
$ make clean; make all
make -C src/ -f Makefile clean
make[1]: Entering directory `/export/home/t_takami/git/gibbslda++/GibbsLDA++-0.2/src'
...
make[1]: Leaving directory `/export/home/t_takami/git/gibbslda++/GibbsLDA++-0.2/src'
$ src/lda --help
Please specify the task you would like to perform (-est/-estc/-inf)!
Command line usage:
lda -est -alpha <double> -beta <double> -ntopics <int> -niters <int> -savestep <int> -twords <int> -dfile <string>
lda -estc -dir <string> -model <string> -niters <int> -savestep <int> -twords <int>
lda -inf -dir <string> -model <string> -niters <int> -twords <int> -dfile <string>
Erstellen Sie eine Datei, in der die im Dokument enthaltenen Wörter durch Leerzeichen getrennt aufgelistet sind, sodass die Anzahl der Dokumente in der ersten Zeile und dann "1 Zeile = 1 Dokument" steht. Wenn Leerzeilen vorhanden sind (Dokumente mit 0 Wörtern, die Features darstellen), tritt ein "Ungültiges (leeres) Dokument!" - Fehler auf.
$ head -n 5 docs.gibbs
13033
Speicheranforderung Karte auswählen Kartengehäuse Antwortmethode Methode Möglich Internes Modell Kapazität Aufzeichnung Aufzeichnung Aufzeichnung Aufzeichnung Zeit einstellen Speichern Speichern Speichern Speichern Speichern
Die Welt, die Welt, die Welt, die wichtigen Dinge, der gesunde Menschenverstand, der gesunde Menschenverstand, der gesunde Menschenverstand, der gesunde Menschenverstand, der gesunde Menschenverstand, der gesunde Menschenverstand, ich
Charakter Kleidung Operation Spiel Blondes Charakter Modell Silberhaar
Best Best Delusion Date Date
Telefon Telefon Telefon Abschied Echtes Geschenk Geschenk Wie Geschenk Wie Bitte Bitte Tränen Tränen Tränen Tränen Narita Gespräch Negative Augen Beziehungsraum Liebe Uruguay Uruguay Uruguay Uruguai Eule Letzte Gefühle hinter den Kulissen…
…
Führen Sie dies aus, indem Sie die Anzahl der Themen $ k $ und die Anzahl der Wiederholungen in der Befehlszeile angeben.
$ src/lda -est -niters 50 -ntopics 10 -twords 5 -dfile docs.gibbs
Sampling 50 iterations!
Iteration 1 ...
...
Iteration 50 ...
Gibbs sampling completed!
Saving the final model!
Wenn Sie fertig sind, sollten Sie einige Dateien haben.
model-final.others
ist der Ausführungsparameter, als dieses Modell erstellt wurde, und wordmap.txt
enthält die dem Wort zugewiesene ID.
$ cat model-final.others
alpha=5.000000
beta=0.100000
ntopics=10
ndocs=13033
nwords=20779
liter=50
$ cat wordmap.txt
20779
T-Shirt 4601
Ai 1829
Aiko 19897
Gruß 2125
...
model-final.twords
listet die charakteristischsten Wörter für jedes Thema auf, wie durch die Option -twords
angegeben (diese Datei wird nicht erstellt, wenn die Option -twords
weggelassen wird).
$ cat model-final.twords
Topic 0th:
Person 0.047465
Fühle 0.019363
Qi 0.018178
Anderes (0.016968
Normal 0.016004
Topic 1th:
Arbeit 0.043820
Zeit 0.024824
Haus 0.019440
Jetzt 0.017962
Mutter 0.016881
Topic 2th:
Wenn 0.033522
Monat 0.018820
Firma 0.018083
Versicherung 0.015252
Anfrage 0.012468
…
model-final.phi
ist die Wahrscheinlichkeit des Auftretens eines Wortes für jedes Thema. 1 Zeile = 1 Thema, und die Anzahl der Spalten in einer Zeile entspricht der Anzahl der Wörter auf dem Korpus. Mit anderen Worten, es ist eine Matrix von "$ k $ Zeilen (Gesamtzahl der Wörter) Spalten". Es sind die numerischen Daten, die die Grundlage für model-final.twords
bilden.
$ head -c 100 model-final.phi
0.000002 0.000002 0.000002 0.000002 0.000799 0.000002 0.000002 0.002415 0.000002 0.000002 0.000002 0
model-final.theta
ist die Wahrscheinlichkeit, dass jedes Dokument zu welchem Thema gehört. Entspricht 1 Zeile = 1 Dokument und 1 Spalte = 1 Thema. Mit anderen Worten, es sind die Matrixdaten von "(Anzahl der Dokumente) Zeilen $ k $ Spalten".
$ head -n 5 model-final.theta
0.081081 0.216216 0.067568 0.067568 0.162162 0.081081 0.067568 0.108108 0.081081 0.067568
0.076923 0.076923 0.123077 0.092308 0.076923 0.076923 0.107692 0.076923 0.076923 0.215385
0.086207 0.103448 0.103448 0.086207 0.137931 0.086207 0.103448 0.086207 0.086207 0.120690
0.090909 0.090909 0.109091 0.127273 0.090909 0.090909 0.090909 0.090909 0.090909 0.127273
0.035971 0.028777 0.111511 0.323741 0.050360 0.086331 0.248201 0.039568 0.028777 0.046763
model-final.tassign
ist eine Liste des Formats [Wort-ID: Thema] für jede Zeile Originaldaten = 1 Dokument.
$ head -n 5 model-final.tassign
0:1 1:4 2:1 3:7 3:7 4:8 4:7 5:5 6:1 6:1 7:4 8:1 9:4 10:1 11:4 11:4 11:4 11:4 12:1 13:0 14:1 14:1 14:1 14:1
15:9 15:9 15:9 16:3 17:6 18:6 19:2 19:9 19:2 19:2 19:9 19:9 20:9 20:9 20:9
21:2 22:9 23:1 24:4 25:6 26:9 9:4 27:4
28:9 28:2 29:9 30:3 30:3
31:4 31:6 31:6 32:3 33:2 34:3 34:3 35:3 35:3 1:5 1:2 36:3 36:3 36:3 37:6 38:2 39:6 40:6 41:6 42:3 42:6 43:6 44:3 …
GibbsLDA ++ ist fast so weit, ein numerisches Modell zu erstellen, dass Sie die anderen Ergebnisse als "Twords" selbst Dokumenten und Wörtern zuordnen müssen.
Persönlich ist es eine R-Sprache, die schwer in die Sprachfunktion zu bekommen ist und ein wenig schüchtern ist, aber lda.collapsed.gibbs.sampler {lda} Wenn Sie sich .collapsed.gibbs.sampler) ansehen, können Sie sehen, dass einige Modelle von Collapsed Gibbs Sampling implementiert sind.
Es scheint keine parallele Verarbeitung (Multi-Core-Unterstützung) oder verteilte Verarbeitung zu unterstützen.
Installieren Sie zuerst die R-Sprache unter CentOS 7.2 (wenn der folgende Befehl "rpm" eine 404 ergibt, löschen Sie den Dateiteil der URL, um die entsprechende Version zu finden).
$ sudo rpm -ihv http://ftp.riken.jp/Linux/fedora/epel/7/x86_64/e/epel-release-7-5.noarch.rpm
$ sudo yum install R
Starten Sie nach Abschluss der R-Installation die interaktive Schnittstelle und installieren Sie das LDA-Paket. Unterwegs versuche ich, das LDA-Paket in "/ usr / lib64 / R / library" zu installieren, aber ich bin kein "root" -Benutzer, daher gebe ich eine persönliche Bibliothek an. Sie werden auch nach der Downloadquelle gefragt. Wählen Sie daher den CRAN-Spiegel für Japan (Tokio).
Unten werden zusätzlich "reshape2" und "ggplot2" installiert, um die Demo auszuführen.
$ R
R version 3.2.3 (2015-12-10) -- "Wooden Christmas-Tree"
Copyright (C) 2015 The R Foundation for Statistical Computing
Platform: x86_64-redhat-linux-gnu (64-bit)
...
> install.packages("lda")
...
Would you like to use a personal library instead? (y/n) y
...
Selection: 13
...
> install.packages("reshape2")
> install.packages("ggplot2")
> require("lda")
> demo(lda)
Es scheint, dass nicht nach der Spezifikationsänderung von ggplot2
stat_count () nicht mit irgendeiner Ästhetik verwendet werden darf.
Wird auftreten und das Diagramm wird nicht angezeigt. Wenn Sie den Teil qplot ()
korrekt und manuell starten, funktioniert er. Da der LDA-Berechnungsprozess selbst abgeschlossen ist, ignorieren Sie ihn und fahren Sie fort.
> top.topic.words(result$topics, 5)
[,1] [,2] [,3] [,4] [,5] [,6]
[1,] "algorithm" "learning" "model" "learning" "neural" "learning"
[2,] "model" "algorithm" "report" "neural" "networks" "network"
[3,] "algorithms" "paper" "models" "networks" "network" "feature"
[4,] "data" "examples" "bayesian" "paper" "learning" "model"
[5,] "results" "number" "technical" "network" "research" "features"
[,7] [,8] [,9] [,10]
[1,] "knowledge" "problem" "paper" "learning"
[2,] "system" "genetic" "decision" "reinforcement"
[3,] "reasoning" "control" "algorithm" "paper"
[4,] "design" "performance" "results" "problem"
[5,] "case" "search" "method" "method"
Die Ergebnisse kommen heraus.
Vokabular zur Verwendung von [
lda.collapsed.gibbs.sampler {lda} `](http://www.inside-r.org/packages/cran/lda/docs/lda.collapsed.gibbs.sampler) Bereiten Sie die Datendateien vor, die "," Dokumenten "entsprechen.
Da vocab
einen Korpus darstellt, erstellen Sie zuerst eine Liste von $ N $ Wörtern (als Zeichenfolgen), die in allen Dokumenten enthalten sind. Dies führt dazu, dass jedes Wort durch einen Index $ i $ auf vocab
dargestellt wird.
{\tt vocab} = \{w_0, w_1, ..., w_{N-1}\} \\
{\tt vocab[}i{\tt]} = w_i
Erstellen Sie als Datendatei einen Korpus von "corpus_r.txt" mit 1 Zeile = 1 Wort. Dies ist eine Sammlung von Wörtern in allen Dokumenten ohne Duplizierung.
$ head -n 5 corpus_r.txt
Assen
Hauptstadt
Person
Tropfen
Lantanoid
$ wc -l corpus_r.txt
20778 corpus_r.txt
documents
ist eine Liste von Dokumenten $ d_k $. Das Dokument $ d_k $ wird durch eine $ m \ times 2 $ -Matrix des Index $ i_ {k, j} $ des im Dokument enthaltenen Wortes und der Anzahl der Vorkommen dieses Wortes im Dokument $ c_j $ dargestellt.
{\tt documents} = \{ d_0, d_1, ..., d_k, ..., d_{m-1} \} \\
d_k = \begin{pmatrix}
i_{k,0} & i_{k,1} & ... & i_{k,n-1} \\
c_{k,0} & c_{k,1} & ... & c_{k,n-1}
\end{pmatrix}
Als Datendatei ist 1 Zeile = 1 Dokument und bereiten Sie "bow_r.txt" mit dem Index (beginnend mit 0) der im Dokument enthaltenen Wörter und der Anzahl der durch einen Doppelpunkt getrennten Vorkommen vor.
$ head -n 5 bow_r.txt
74:1 1109:1 1788:1 7000:2 10308:2 10552:1 12332:2 13489:1 14996:1 15448:1 15947:1 16354:4 17577:1 18262:1 19831:4
3256:3 5278:1 9039:1 12247:1 14529:6 17026:3
2181:1 4062:1 6270:1 6508:1 7405:1 8662:1 15448:1 18905:1
8045:2 9323:1 5934:2
288:3 624:1 691:1 820:2 1078:2 1109:2 1148:3 1251:1 2025:1 2050:1 2072:1 2090:1 2543:2 2626:1 2759:1…
$ wc -l bow_r.txt
13017 bow_r.txt
Führen Sie es mit dem folgenden Code aus. Es ist größer, die Datendatei zu analysieren und die angenommene Datenstruktur zu erstellen als die LDA-Verarbeitung (vielleicht ist es einfacher zu schreiben, wenn Sie gut in R sind?).
require("lda")
vocab <- as.vector(read.table("corpus_r.txt", header=FALSE)$V1)
file <- file("bow_r.txt", "r")
docs <- list()
repeat {
line <- readLines(con=file, 1)
if(length(line) == 0) break
doc <- NULL
for(tc in strsplit(line, "\t")[[1]]){
col <- c()
for(c in strsplit(tc, ":")[[1]]){
col <- c(col, as.integer(c))
}
if(is.null(doc)) doc <- cbind(col)
else doc <- cbind(doc, col)
}
docs <- append(docs, list(doc))
}
close(file)
result = lda.collapsed.gibbs.sampler(docs, 100, vocab, 50, 0.1, 0.1)
top.topic.words(result$topics, 5)
Wenn Sie "top.topic.words ()" ausführen, werden die Wörter aufgelistet, die jedes der $ k = 100 $ -Themen charakterisieren.
[,1] [,2] [,3] [,4] [,5] [,6] [,7] [,8]
[1,] "Problem" "Zeitraum" "Ichiban" "Auge" "Zimmer" "Problem" "Idol" "Box"
[2,] "Kongressabgeordnete" "Bitte" "Wetter" "Sperren" "Haus" "von jetzt an" "Ventilator" "Teil"
[3,] "Gesellschaft" "Versuch" "China" "Drehung" "Toilette" "Tempel" "Seltsam" "Aufkleber"
[4,] "Religion" "jedermann" "Fehler" "Nicht notwendig" "Wasser" "Unmöglich" "Interesse" "Lack"
[5,] "Prinzip" "Vollzeitangestellter" "Alles" "China" "Waschen" "Inhalt" "Gehorsam" "Information"
[,9] [,10] [,11] [,12] [,13] [,14] [,15] [,16]
[1,] "Weiblich" "Silber" "Bild" "Seite? ˅" "Lied" "Bitte" "Schaltkreis" "Arbeitsplätze"
[2,] "Mann" "Kurzsichtigkeit" "Anhang" "Methode" "Bitte" "Meine" "Regiment" "Unternehmen"
[3,] "männlich" "aufgewachsen" "Mehrere" "Anmeldung" "Klavier" "Grund" "Infanterie" "Boss"
[4,] "Mann" "Snack" "Foto" "Domain" "Musik" "Der Umsatz" "Aktuell" "Mann"
[5,] "Frau" "Bilderbuch" "Erde" "Seite" "Gefühl" "Nummer" "Foto" "Arbeitsplatz"
... (Fortsetzung bis zu 100 Themen)
Recommended Posts