2012-10-10 20 views
11

Ngram sayılarını bir sınıflandırıcı özellik olarak kullanan bir kağıt okudum ve bunun tam olarak ne anlama geldiğini merak ediyordum.ngram sayılar ve nltk kullanarak nasıl uygulanır?

Örnek metin: Ben tanımlamak zorunda bu metinde, dışarı vb Ben unigrams oluşturabilir

, Bigramlar, trigramlar "Lorem ipsum dolor, amet sed diam consetetur sadipscing elitr oturmak" hangi "seviye üzerinde "bu unigramları oluşturmak için. "Seviye", karakter, hece, kelime olabilir ...

Yukarıdaki cümleden tekdüze oluşturmak, tüm sözcüklerin bir listesini oluşturabilir mi?

İkigram oluşturmak, kelime çiftlerinin birbirini takip eden kelimeleri bir araya getirmesiyle sonuçlanabilir? Kağıt, ngram sayıları hakkında konuşursa, metinden yalnızca unigramlar, bigramlar, trigramlar vb. Oluşturur ve hangi ngramın ne sıklıkta oluştuğunu sayar?

Python'un nltk paketinde mevcut bir yöntem var mı? Yoksa kendi başıma bir versiyonunu uygulamak zorunda mıyım?

+1

Sevgiler ortak bir yorumdur verir, ama

unigrams = {} for token in tokens: if token not in unigrams: unigrams[token] = 1 else: unigrams[token] += 1 

"gram," birim olabilir, örneğin bayt veya karakter de. Yani bir sürgülü pencere kullanıyorsanız "lorem" in karakteri 3 gram "lor" ve "em", hatta "lor", "cevher", "rem" olabilir. – tripleee

cevap

15

Eski kodumu buldum, belki yararlıdır.

import nltk 
from nltk import bigrams 
from nltk import trigrams 

text="""Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nullam ornare 
tempor lacus, quis pellentesque diam tempus vitae. Morbi justo mauris, 
congue sit amet imperdiet ipsum dolor sit amet, consectetur adipiscing elit. Nullam ornare 
tempor lacus, quis pellentesque diam""" 
# split the texts into tokens 
tokens = nltk.word_tokenize(text) 
tokens = [token.lower() for token in tokens if len(token) > 1] #same as unigrams 
bi_tokens = bigrams(tokens) 
tri_tokens = trigrams(tokens) 

# print trigrams count 

print [(item, tri_tokens.count(item)) for item in sorted(set(tri_tokens))] 
>>> 
[(('adipiscing', 'elit.', 'nullam'), 2), (('amet', 'consectetur', 'adipiscing'), 2),(('amet', 'imperdiet', 'ipsum'), 1), (('congue', 'sit', 'amet'), 1), (('consectetur', 'adipiscing', 'elit.'), 2), (('diam', 'tempus', 'vitae.'), 1), (('dolor', 'sit', 'amet'), 2), (('elit.', 'nullam', 'ornare'), 2), (('imperdiet', 'ipsum', 'dolor'), 1), (('ipsum', 'dolor', 'sit'), 2), (('justo', 'mauris', 'congue'), 1), (('lacus', 'quis', 'pellentesque'), 2), (('lorem', 'ipsum', 'dolor'), 1), (('mauris', 'congue', 'sit'), 1), (('morbi', 'justo', 'mauris'), 1), (('nullam', 'ornare', 'tempor'), 2), (('ornare', 'tempor', 'lacus'), 2), (('pellentesque', 'diam', 'tempus'), 1), (('quis', 'pellentesque', 'diam'), 2), (('sit', 'amet', 'consectetur'), 2), (('sit', 'amet', 'imperdiet'), 1), (('tempor', 'lacus', 'quis'), 2), (('tempus', 'vitae.', 'morbi'), 1), (('vitae.', 'morbi', 'justo'), 1)] 
+0

Kodunuz için teşekkürler! – akohout

+0

Aynı cümle içinde değilse, ['tempus', 'vitae', 'morbi'] bir trigram olarak sayılması doğru mu? – Mouscellaneous

-1

Bunun için nltk'de özel bir yöntem olduğunu sanmıyorum. Bu zor değil. Eğer n kelimelerin bir cümlesine sahipseniz (kelime seviyesini kullandığınızı varsayarak), tüm ngram uzunluğunu 1-n alın, bu ngramların her birinden yineleyin ve sayıları sayımla birlikte bir ilişkilendirici dizide tuşlayın. 30'dan fazla kod içermemeli, bunun için kendi paketinizi oluşturabilir ve gerektiğinde içe aktarabilirsiniz.

+1

Tamam, o zaman ngram doğru düzgün anladım gibi görünüyor :) – akohout

2

N-gramları sayarsanız, saymayı kullanmak yerine hash tablosunu (sözlük) kullanmak daha iyidir. Yukarıdaki örnek için: Bu, (n) zaman karmaşıklığı O

+1

Bu bir cevap mı? eğer öyleyse lütfen detayları ile paylaşın. – Sachith