2016-12-24 83 views
3

我希望能夠判斷句子在python中是否真的有意義。例如在python中按句子結構對文本進行分類

Hello, how are you today? --> Correct 
Hello, are today are how --> Incorrect 

到目前爲止,我有這個代碼執行以下操作:

1 - 獲取從nltk.browns語料庫20 000句。
2 - 混淆了最後的10成000句的話(不正確的數據)
3 - 標籤使用斯坦福POS標註器

from nltk.corpus import brown 
from nltk.tokenize import sent_tokenize, word_tokenize 
from nltk.classify import accuracy 
from nltk.tag import StanfordPOSTagger 
from nltk import pos_tag 
import string 
import random 

PUNC = [x for x in string.punctuation] + ["''", "``"] 

def download_data(target_path): 
    brown_data = brown.sents() 
    i = 0; n = 0 
    with open(target_path, 'w') as data_file: 
     while n < 20000: 
      for sent in sent_tokenize(' '.join(brown_data[i])): 
       updated_list = [x for x in word_tokenize(sent) if x not in PUNC] 
       if n > 10000: 
        random.shuffle(updated_list) 
       sent = ' '.join(updated_list) + '\n' 
       if sent != '\n': 
        data_file.write(sent) 
        n += 1 
       i += 1 

def get_data(data_path): 
    with open(data_path, 'r') as data_file: 
     return [x for x in data_file.readlines()] 

def parse_data(data, tagger): 
    parsed_data = [] 
    for i in range(len(data)): 
     if i > 10000: 
      parsed_data.append((tagger.tag(word_tokenize(data[i].replace('\n', ''))), False)) 
     else: 
      parsed_data.append((tagger.tag(word_tokenize(data[i].replace('\n', ''))), True)) 
    random.shuffle(parsed_data) 
    return parsed_data[:15000], parsed_data[15000:] 

if __name__ == '__main__': 
    data_path = 'data.txt' 

    stanford_jar_path = 'stanford-postagger.jar' 
    stanford_model_path = 'models/english-bidirectional-distsim.tagger' 

    tagger = StanfordPOSTagger(model_filename=stanford_model_path, 
           path_to_jar=stanford_jar_path) 

    #download_data(data_path) 
    all_data = get_data(data_path) 
    train_data, test_data = parse_data(all_data, tagger) 

所以,我怎麼能培養例如分類,分類所有句子根據我提供的數據,新文本是正確的還是不正確的?

如果有人有更好的建議,我也打開。

+0

從技術上講,正確地解決這些問題的方法當然是(a)根據您感興趣的領域的文本(某種RNN/LSTM,如果您想進行尖端工作)來訓練語言模型,然後(b)針對已知的好壞句子集合建立可接受的概率截止點,最後(c)使用模型爲您提供的新句子的句子概率,以分離您的二元情況。類似於現有的答案,您應該首先確定這是否值得,但是,使用快速而簡潔的二元或三元模型。 – fnl

回答

0

我會看看存在/不存在部分演講的部分。你的例子可以轉化成以下POS繼承序列:

[('NNP', 'VBP'), ('VBP', 'NN'), ('NN', 'VBP'), ('VBP', 'WRB')] # incorrect 
[('NNP', 'WRB'), ('WRB', 'VBP'), ('VBP', 'PRP'), ('PRP', 'NN')] # correct 

如果二階帶來的所有可能的組合,並建立0和1的特徵向量,就可以使用這些向量來訓練你的算法。

0

當您需要爲您的訓練集創建功能時,您正處於這一步。我會使用2和3個單詞n-gram作爲特徵,並且可能使用2和3個長度的n-gram POS。因此,舉例來說,你會把所有的句子都找出來,找到所有的bi/trigrams並將它們二進制化(如果當前句子不包含它們,則使它們爲0,如果它包含,則使它們爲1)。我會爲POS做同樣的事情。製作POS的二進制/三進制文件並對其進行二進制化。然後你可以使用像天真貝葉這樣的東西來看看是否有任何預測能力存在。

+0

會添加n-gram作爲功能和位置作爲功能可以提高精確度而不僅僅是正位? –

+0

我認爲會有一些預測能力,因爲'棕色狐狸'應該比'狐狸棕色'更頻繁地出現。有一些單詞的組合不會出現在彼此相鄰的句子中。當然,你應該憑經驗進行測試。 –

+0

我會如何二元化它們?我會以0和1的長串結束嗎? @TedPetrou –

0

考慮使用詞性標記雖然不錯,但我相信考慮n-gram語言模型應該足夠適合您的任務。在這裏,我的假設是,POS標籤在數量上很少(根據Penn Treebank爲36),所以與語料庫的詞彙量相比,變體的數量會更少。所以,POS標籤可能會給你很好的表現,但它也可能誤導你的分類器。 (我的個人意見)

你可以做最多五克語言模型的實驗。所有的n元組將成爲分類器的特徵。請注意,更高數量的n-gram會增加複雜性,但應該會導致更高的準確性。

對於分類,您可以考慮生成模型和判別模型。對於生成模型,您可以考慮Naive-Bayes和區分性模型,您可以考慮SVM或Logistic迴歸。這些分類器在文本分類任務中運行良好。