복붙노트

[PYTHON] 감정 분석을위한 nltk NaiveBayesClassifier 교육

PYTHON

감정 분석을위한 nltk NaiveBayesClassifier 교육

문장을 사용하여 Python에서 NaiveBayesClassifier를 교육 중이며 아래 오류가 표시됩니다. 나는 그 오류가 무엇인지 이해하지 못한다. 그리고 어떤 도움도 좋을 것이다.

많은 다른 입력 형식을 시도했지만 오류가 남아 있습니다. 아래에 주어진 코드 :

from text.classifiers import NaiveBayesClassifier
from text.blob import TextBlob
train = [('I love this sandwich.', 'pos'),
         ('This is an amazing place!', 'pos'),
         ('I feel very good about these beers.', 'pos'),
         ('This is my best work.', 'pos'),
         ("What an awesome view", 'pos'),
         ('I do not like this restaurant', 'neg'),
         ('I am tired of this stuff.', 'neg'),
         ("I can't deal with this", 'neg'),
         ('He is my sworn enemy!', 'neg'),
         ('My boss is horrible.', 'neg') ]

test = [('The beer was good.', 'pos'),
        ('I do not enjoy my job', 'neg'),
        ("I ain't feeling dandy today.", 'neg'),
        ("I feel amazing!", 'pos'),
        ('Gary is a friend of mine.', 'pos'),
        ("I can't believe I'm doing this.", 'neg') ]
classifier = nltk.NaiveBayesClassifier.train(train)

나는 아래에 추적을 포함하고있다.

Traceback (most recent call last):
  File "C:\Users\5460\Desktop\train01.py", line 15, in <module>
    all_words = set(word.lower() for passage in train for word in word_tokenize(passage[0]))
  File "C:\Users\5460\Desktop\train01.py", line 15, in <genexpr>
    all_words = set(word.lower() for passage in train for word in word_tokenize(passage[0]))
  File "C:\Python27\lib\site-packages\nltk\tokenize\__init__.py", line 87, in word_tokenize
    return _word_tokenize(text)
  File "C:\Python27\lib\site-packages\nltk\tokenize\treebank.py", line 67, in tokenize
    text = re.sub(r'^\"', r'``', text)
  File "C:\Python27\lib\re.py", line 151, in sub
    return _compile(pattern, flags).sub(repl, string, count)
TypeError: expected string or buffer

해결법

  1. ==============================

    1.데이터 구조를 변경해야합니다. 현재 기차 목록이 있습니다.

    데이터 구조를 변경해야합니다. 현재 기차 목록이 있습니다.

    >>> train = [('I love this sandwich.', 'pos'),
    ('This is an amazing place!', 'pos'),
    ('I feel very good about these beers.', 'pos'),
    ('This is my best work.', 'pos'),
    ("What an awesome view", 'pos'),
    ('I do not like this restaurant', 'neg'),
    ('I am tired of this stuff.', 'neg'),
    ("I can't deal with this", 'neg'),
    ('He is my sworn enemy!', 'neg'),
    ('My boss is horrible.', 'neg')]
    

    그러나 문제는 각 튜플의 첫 번째 요소는 기능 사전이어야한다는 것입니다. 따라서 목록을 분류 자로 작업 할 수있는 데이터 구조로 변경합니다.

    >>> from nltk.tokenize import word_tokenize # or use some other tokenizer
    >>> all_words = set(word.lower() for passage in train for word in word_tokenize(passage[0]))
    >>> t = [({word: (word in word_tokenize(x[0])) for word in all_words}, x[1]) for x in train]
    

    이제 데이터가 다음과 같이 구성되어야합니다.

    >>> t
    [({'this': True, 'love': True, 'deal': False, 'tired': False, 'feel': False, 'is': False, 'am': False, 'an': False, 'sandwich': True, 'ca': False, 'best': False, '!': False, 'what': False, '.': True, 'amazing': False, 'horrible': False, 'sworn': False, 'awesome': False, 'do': False, 'good': False, 'very': False, 'boss': False, 'beers': False, 'not': False, 'with': False, 'he': False, 'enemy': False, 'about': False, 'like': False, 'restaurant': False, 'these': False, 'of': False, 'work': False, "n't": False, 'i': False, 'stuff': False, 'place': False, 'my': False, 'view': False}, 'pos'), . . .]
    

    각 튜플의 첫 번째 요소는 현재 사전입니다. 이제 데이터가 제자리에 있고 각 튜플의 첫 번째 요소가 사전이되었으므로 다음과 같이 분류자를 학습 할 수 있습니다.

    >>> import nltk
    >>> classifier = nltk.NaiveBayesClassifier.train(t)
    >>> classifier.show_most_informative_features()
    Most Informative Features
                        this = True              neg : pos    =      2.3 : 1.0
                        this = False             pos : neg    =      1.8 : 1.0
                          an = False             neg : pos    =      1.6 : 1.0
                           . = True              pos : neg    =      1.4 : 1.0
                           . = False             neg : pos    =      1.4 : 1.0
                     awesome = False             neg : pos    =      1.2 : 1.0
                          of = False             pos : neg    =      1.2 : 1.0
                        feel = False             neg : pos    =      1.2 : 1.0
                       place = False             neg : pos    =      1.2 : 1.0
                    horrible = False             pos : neg    =      1.2 : 1.0
    

    분류 기준을 사용하려면 다음과 같이하십시오. 먼저 테스트 문장으로 시작합니다.

    >>> test_sentence = "This is the best band I've ever heard!"
    

    그런 다음, 문장을 토큰 화하여 문장이 all_words와 어떤 단어를 공유하는지 파악하십시오. 이것들은 문장의 특징을 구성합니다.

    >>> test_sent_features = {word.lower(): (word in word_tokenize(test_sentence.lower())) for word in all_words}
    

    이제 기능이 다음과 같이 보입니다.

    >>> test_sent_features
    {'love': False, 'deal': False, 'tired': False, 'feel': False, 'is': True, 'am': False, 'an': False, 'sandwich': False, 'ca': False, 'best': True, '!': True, 'what': False, 'i': True, '.': False, 'amazing': False, 'horrible': False, 'sworn': False, 'awesome': False, 'do': False, 'good': False, 'very': False, 'boss': False, 'beers': False, 'not': False, 'with': False, 'he': False, 'enemy': False, 'about': False, 'like': False, 'restaurant': False, 'this': True, 'of': False, 'work': False, "n't": False, 'these': False, 'stuff': False, 'place': False, 'my': False, 'view': False}
    

    그런 다음 해당 기능을 간단하게 분류합니다.

    >>> classifier.classify(test_sent_features)
    'pos' # note 'best' == True in the sentence features above
    

    이 테스트 문장은 긍정적 인 것으로 보입니다.

  2. ==============================

    2.@ 275365의 NLTK 베이지안 분류기에 대한 데이터 구조에 대한 자습서는 훌륭합니다. 보다 높은 수준에서 볼 때,

    @ 275365의 NLTK 베이지안 분류기에 대한 데이터 구조에 대한 자습서는 훌륭합니다. 보다 높은 수준에서 볼 때,

    우리는 정서 태그로 문장을 입력했습니다 :

    training_data = [('I love this sandwich.', 'pos'),
    ('This is an amazing place!', 'pos'),
    ('I feel very good about these beers.', 'pos'),
    ('This is my best work.', 'pos'),
    ("What an awesome view", 'pos'),
    ('I do not like this restaurant', 'neg'),
    ('I am tired of this stuff.', 'neg'),
    ("I can't deal with this", 'neg'),
    ('He is my sworn enemy!', 'neg'),
    ('My boss is horrible.', 'neg')]
    

    우리의 피처 세트가 개별적인 단어라고 생각해 봅시다. 그래서 우리는 훈련 데이터로부터 가능한 모든 단어의 목록을 추출합니다 (단어를 보자).

    from nltk.tokenize import word_tokenize
    from itertools import chain
    vocabulary = set(chain(*[word_tokenize(i[0].lower()) for i in training_data]))
    

    본질적으로, 여기 어휘는 @ 275365의 all_word와 같습니다.

    >>> all_words = set(word.lower() for passage in training_data for word in word_tokenize(passage[0]))
    >>> vocabulary = set(chain(*[word_tokenize(i[0].lower()) for i in training_data]))
    >>> print vocabulary == all_words
    True
    

    각 데이터 포인트 (예 : 각 문장 및 pos / neg 태그)에서 우리는 지형지 물 (즉 어휘의 단어)이 존재하는지 여부를 말하고 싶습니다.

    >>> sentence = word_tokenize('I love this sandwich.'.lower())
    >>> print {i:True for i in vocabulary if i in sentence}
    {'this': True, 'i': True, 'sandwich': True, 'love': True, '.': True}
    

    그러나 우리는 어떤 단어가 문장에 존재하지 않지만 어휘에 존재 하는지를 분류 자에게 알려주기를 원하므로 각 데이터 포인트에 대해 가능한 모든 단어를 어휘에 나열하고 단어의 존재 여부를 말합니다.

    >>> sentence = word_tokenize('I love this sandwich.'.lower())
    >>> x =  {i:True for i in vocabulary if i in sentence}
    >>> y =  {i:False for i in vocabulary if i not in sentence}
    >>> x.update(y)
    >>> print x
    {'love': True, 'deal': False, 'tired': False, 'feel': False, 'is': False, 'am': False, 'an': False, 'good': False, 'best': False, '!': False, 'these': False, 'what': False, '.': True, 'amazing': False, 'horrible': False, 'sworn': False, 'ca': False, 'do': False, 'sandwich': True, 'very': False, 'boss': False, 'beers': False, 'not': False, 'with': False, 'he': False, 'enemy': False, 'about': False, 'like': False, 'restaurant': False, 'this': True, 'of': False, 'work': False, "n't": False, 'i': True, 'stuff': False, 'place': False, 'my': False, 'awesome': False, 'view': False}
    

    그러나이 작업은 어휘를 두 번 반복하므로이 작업을 더 효율적으로 수행 할 수 있습니다.

    >>> sentence = word_tokenize('I love this sandwich.'.lower())
    >>> x = {i:(i in sentence) for i in vocabulary}
    {'love': True, 'deal': False, 'tired': False, 'feel': False, 'is': False, 'am': False, 'an': False, 'good': False, 'best': False, '!': False, 'these': False, 'what': False, '.': True, 'amazing': False, 'horrible': False, 'sworn': False, 'ca': False, 'do': False, 'sandwich': True, 'very': False, 'boss': False, 'beers': False, 'not': False, 'with': False, 'he': False, 'enemy': False, 'about': False, 'like': False, 'restaurant': False, 'this': True, 'of': False, 'work': False, "n't": False, 'i': True, 'stuff': False, 'place': False, 'my': False, 'awesome': False, 'view': False}
    

    따라서 각 문장마다 분류기에 단어가 존재하는 단어와 그렇지 않은 단어의 각 문장을 알려주고 pos / neg 태그도 지정합니다. 이것을 feature_set이라고 부를 수 있습니다. 위의 x와 그 태그로 구성된 튜플입니다.

    >>> feature_set = [({i:(i in word_tokenize(sentence.lower())) for i in vocabulary},tag) for sentence, tag in training_data]
    [({'this': True, 'love': True, 'deal': False, 'tired': False, 'feel': False, 'is': False, 'am': False, 'an': False, 'sandwich': True, 'ca': False, 'best': False, '!': False, 'what': False, '.': True, 'amazing': False, 'horrible': False, 'sworn': False, 'awesome': False, 'do': False, 'good': False, 'very': False, 'boss': False, 'beers': False, 'not': False, 'with': False, 'he': False, 'enemy': False, 'about': False, 'like': False, 'restaurant': False, 'these': False, 'of': False, 'work': False, "n't": False, 'i': False, 'stuff': False, 'place': False, 'my': False, 'view': False}, 'pos'), ...]
    

    그런 다음 우리는 feature_set의 이러한 기능과 태그를 분류기에 입력하여이를 교육합니다.

    from nltk import NaiveBayesClassifier as nbc
    classifier = nbc.train(feature_set)
    

    이제 훈련 된 분류기가 있고 새 문장에 태그를 추가하려는 경우 새 문장의 단어 중 어떤 단어가 분류 자의 학습 된 어휘에 있는지 확인하기 위해 새 문장을 "완성"해야합니다.

    >>> test_sentence = "This is the best band I've ever heard! foobar"
    >>> featurized_test_sentence = {i:(i in word_tokenize(test_sentence.lower())) for i in vocabulary}
    

    참고 : 위의 단계에서 알 수 있듯이, 경험이있는 사용자는 foobar 토큰이 사라지기 때문에 순진한 베이 분류기에서 어휘 단어를 처리 할 수 ​​없습니다.

    그런 다음 특성화 된 테스트 문장을 분류 자에게 공급하고 분류 할 것을 요청합니다.

    >>> classifier.classify(featurized_test_sentence)
    'pos'
    

    다행히도 NLTK의 순수한 베이 즈 분류기에 대한 감상적인 분석을 위해 데이터를 입력하는 방법에 대한 명확한 그림이 있기를 바랍니다. 다음은 주석과 연습이없는 전체 코드입니다.

    from nltk import NaiveBayesClassifier as nbc
    from nltk.tokenize import word_tokenize
    from itertools import chain
    
    training_data = [('I love this sandwich.', 'pos'),
    ('This is an amazing place!', 'pos'),
    ('I feel very good about these beers.', 'pos'),
    ('This is my best work.', 'pos'),
    ("What an awesome view", 'pos'),
    ('I do not like this restaurant', 'neg'),
    ('I am tired of this stuff.', 'neg'),
    ("I can't deal with this", 'neg'),
    ('He is my sworn enemy!', 'neg'),
    ('My boss is horrible.', 'neg')]
    
    vocabulary = set(chain(*[word_tokenize(i[0].lower()) for i in training_data]))
    
    feature_set = [({i:(i in word_tokenize(sentence.lower())) for i in vocabulary},tag) for sentence, tag in training_data]
    
    classifier = nbc.train(feature_set)
    
    test_sentence = "This is the best band I've ever heard!"
    featurized_test_sentence =  {i:(i in word_tokenize(test_sentence.lower())) for i in vocabulary}
    
    print "test_sent:",test_sentence
    print "tag:",classifier.classify(featurized_test_sentence)
    
  3. ==============================

    3.TextBlob을 사용하려하지만 NLTK NaiveBayesClassifier를 교육하고있는 것으로 보입니다. 다른 답변에서 지적했듯이 사전에 기능 사전을 전달해야합니다.

    TextBlob을 사용하려하지만 NLTK NaiveBayesClassifier를 교육하고있는 것으로 보입니다. 다른 답변에서 지적했듯이 사전에 기능 사전을 전달해야합니다.

    TextBlob에는 훈련 세트의 어떤 단어가 문서에 포함되어 있는지 (다른 답변에서 보여지는 것처럼) 나타내는 기본 피쳐 추출기가 있습니다. 따라서 TextBlob를 사용하면 데이터를 그대로 전달할 수 있습니다.

    from textblob.classifiers import NaiveBayesClassifier
    
    train = [('This is an amazing place!', 'pos'),
            ('I feel very good about these beers.', 'pos'),
            ('This is my best work.', 'pos'),
            ("What an awesome view", 'pos'),
            ('I do not like this restaurant', 'neg'),
            ('I am tired of this stuff.', 'neg'),
            ("I can't deal with this", 'neg'),
            ('He is my sworn enemy!', 'neg'),
            ('My boss is horrible.', 'neg') ] 
    test = [
            ('The beer was good.', 'pos'),
            ('I do not enjoy my job', 'neg'),
            ("I ain't feeling dandy today.", 'neg'),
            ("I feel amazing!", 'pos'),
            ('Gary is a friend of mine.', 'pos'),
            ("I can't believe I'm doing this.", 'neg') ] 
    
    
    classifier = NaiveBayesClassifier(train)  # Pass in data as is
    # When classifying text, features are extracted automatically
    classifier.classify("This is an amazing library!")  # => 'pos'
    

    물론 간단한 기본 추출기는 모든 문제에 적절하지 않습니다. 지형지 물을 추출하는 방법을 원한다면 텍스트 문자열을 입력으로 사용하여 기능 사전을 출력하고이를 분류 자로 전달하는 함수를 작성하면됩니다.

    classifier = NaiveBayesClassifier(train, feature_extractor=my_extractor_func)
    

    간단한 TextBlob 분류 자 ​​자습서를 다음에서 확인하시기 바랍니다. http://textblob.readthedocs.org/en/latest/classifiers.html

  4. from https://stackoverflow.com/questions/20827741/nltk-naivebayesclassifier-training-for-sentiment-analysis by cc-by-sa and MIT license