Raggruppare un lungo elenco di stringhe (parole) in gruppi di somiglianza


31

Ho a portata di mano il seguente problema: ho un lungo elenco di parole, possibilmente nomi, cognomi, ecc. Devo raggruppare questo elenco di parole, in modo che parole simili, ad esempio parole con una simile modifica (Levenshtein) compaiano nella stesso cluster. Ad esempio "algoritmo" e "alogritmo" dovrebbero avere alte probabilità di apparire nello stesso cluster.

Sono ben consapevole dei classici metodi di clustering senza supervisione come il clustering k-mean, il clustering EM nella letteratura del Pattern Recognition. Il problema qui è che questi metodi funzionano su punti che risiedono in uno spazio vettoriale. Ho parole di stringhe alla mia mano qui. Sembra che la domanda su come rappresentare le stringhe in uno spazio vettoriale numerico e calcolare i "mezzi" dei cluster di stringhe non abbia una risposta sufficiente, secondo i miei sforzi di indagine fino ad ora. Un approccio ingenuo per attaccare questo problema sarebbe quello di combinare i cluster di k-medie con la distanza di Levenshtein, ma rimane ancora la domanda "Come rappresentare" significa "di stringhe?". Esiste un peso chiamato peso TF-IDF, ma sembra che sia principalmente correlato all'area del clustering dei "documenti di testo", non al clustering di singole parole. http://pike.psu.edu/cleandb06/papers/CameraReady_120.pdf

La mia ricerca in quest'area continua ancora, ma volevo anche prendere idee da qui. Cosa consiglieresti in questo caso, qualcuno è a conoscenza di metodi per questo tipo di problema?


1
Ho appreso dell'esistenza di una variante di k-mean denominata "K-medoids". en.wikipedia.org/wiki/K-medoids Non funziona con la distanza euclidea L2 e non ha bisogno del calcolo dei mezzi. Utilizza il punto dati più vicino agli altri in un cluster come "medoid".
Ufuk Can Bicici,

1
It seems that there are some special string clustering algorithms. Se provieni da un campo specifico di mining del testo, non da statistiche / analisi dei dati, questa dichiarazione è giustificata. Tuttavia, se impari a conoscere il ramo del cluster così com'è, troverai che non esistono algoritmi "speciali" per i dati delle stringhe. Lo "speciale" è come pre-elaborare tali dati prima di immetterli in un'analisi del cluster.
ttnphns,


Nota la differenza tra Affinity Propagation e K-Means clustering e come influenzerà il tempo di calcolo. quora.com/…
Gabriel Alon,

Risposte:


37

Raccomandazione di Seconding @ Mican per la propagazione dell'affinità .

Dall'articolo: L Frey, Brendan J. e Delbert Dueck. "Clustering passando messaggi tra punti dati." scienza 315.5814 (2007): 972-976. .

È super facile da usare tramite molti pacchetti. Funziona su qualsiasi cosa tu possa definire la somiglianza a coppie. Che puoi ottenere moltiplicando la distanza di Levenshtein per -1.

Ho messo insieme un breve esempio usando il primo paragrafo della tua domanda come input. In Python 3:

import numpy as np
import sklearn.cluster
import distance

words = "YOUR WORDS HERE".split(" ") #Replace this line
words = np.asarray(words) #So that indexing with a list will work
lev_similarity = -1*np.array([[distance.levenshtein(w1,w2) for w1 in words] for w2 in words])

affprop = sklearn.cluster.AffinityPropagation(affinity="precomputed", damping=0.5)
affprop.fit(lev_similarity)
for cluster_id in np.unique(affprop.labels_):
    exemplar = words[affprop.cluster_centers_indices_[cluster_id]]
    cluster = np.unique(words[np.nonzero(affprop.labels_==cluster_id)])
    cluster_str = ", ".join(cluster)
    print(" - *%s:* %s" % (exemplar, cluster_str))

L'output era (esempi in corsivo a sinistra del cluster di cui sono esemplari):

  • avere: possibilità, modifica, mano, avere, alto
  • seguente: seguente
  • problema: problema
  • I: I, a, at, etc, in, list, of
  • possibilmente: possibilmente
  • cluster: cluster
  • parola: perché, e, a lungo, bisogno, dovrebbe, molto, parola, parole
  • simile: simile
  • Levenshtein: Levenshtein
  • distanza: distanza
  • il: quello, il, questo, a, con
  • stesso: esempio, elenco, nomi, stesso, tale, cognomi
  • algoritmo: algoritmo, alogritmo
  • compare: appare, appare

Eseguendolo su un elenco di 50 nomi casuali :

  • Diane: Deana, Diane, Dionne, Gerald, Irina, Lisette, Minna, Nicki, Ricki
  • Jani: Clair, Jani, Jason, Jc, Kimi, Lang, Marcus, Maxima, Randi, Raul
  • Verline: Destiny, Kellye, Marylin, Mercedes, Sterling, Verline
  • Glenn: Elenor, Glenn, Gwenda
  • Armandina: Armandina, Augustina
  • Shiela: Ahmed, Estella, Milissa, Shiela, Thresa, Wynell
  • Laureen: autunno, Haydee, Laureen, Lauren
  • Alberto: Albertha, Alberto, Robert
  • Lore: Ammie, Doreen, Eura, Josef, Lore, Lori, Porter

Mi sembra abbastanza bello (è stato divertente).


è possibile avere lo stesso algoritmo usando solo sklearn? o usare scipy.spatial.distance con il martellamento? qual è il vantaggio di usare levenshtein? Immagino che dovrò provare a usare questa domanda: stackoverflow.com/questions/4588541/…
pierre

1
@pierre Levenshtein è ciò che definirei una "distanza di controllo ortografico", è un buon proxy per la possibilità di un errore di ortografia umana. Damerau Levenshtein potrebbe anche essere migliore. Non so che la distanza di Hamming sia definita per stringhe di lunghezza diversa. Permette solo scambi, non inserimenti. determinare come riempire / tagliare la corda nel modo più ragionevole è difficile quasi quanto calcolare la distanza di Levenshtein. Dovresti tagliare / tagliare l'inizio? Fine? Alcuni dalla metà?
Lyndon White,

Se volevi davvero evitare la dipendenza dalle distanze. potresti usare l' implementazione del codice Rossetta
Lyndon White,

leggendo en.wikipedia.org/wiki/Damerau%E2%80%93Levenshtein_distance posso vedere come la trasposizione può fare la differenza specialmente per refuso e python ha un nuovo pacchetto per questo. Vedo come posso usarlo contro un elenco di parole e ottenere il "più vicino" ma potrebbe non essere il più importante. Devo ottenere la mia lista e verificare con tf-idf. Fantastico grazie
pierre

1
@dduhaime quasi certamente. In generale, la propagazione dell'affinità funziona per perferenze non sinatriche, ma poiché questo è simmetrico, andare avanti. Sono sicuro che qualcosa in SciPy abbia un tipo di matrice triangolare che assomiglia a una matrice completa. Sono stato nella terra di Julia Lang troppo a lungo e non riesco a ricordare come questo è fatto in Python. (In julia lo useresti Symmetric)
Lyndon White,

5

Utilizzare algoritmi di clustering di grafici, come cluster di Louvain, Restricted Neighborhood Search Clustering (RNSC), Affinity Propgation Clustering (APC) o algoritmo Markov Cluster (MCL).


Che dire del metodo K-medoids che ho trovato? Devo implementare questa soluzione il prima possibile, quindi mi è sembrata una buona soluzione. Sono consapevole dell'esistenza di questi metodi basati su grafici, ma temo di non potermi permettere il tempo necessario per comprenderli e implementarli.
Ufuk Can Bicici,

Per tutti loro il software è disponibile con accordi di licenza abbastanza non restrittivi, come GNU GPL. Non sono un grande fan del tipo di algoritmo k-mediods principalmente a causa del parametro k ma dipende da te naturalmente. Se hai bisogno di un'implementazione interna, penso che APC e MCL siano probabilmente i più facili da implementare. Se dovessi farlo, provali prima ovviamente.
Micans,

2

Potresti provare il modello dello spazio vettoriale con gli n-grammi delle parole come voci dello spazio vettoriale. Penso che dovresti usare una misura come la somiglianza del coseno in questo caso invece di modificare la distanza.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.