Làm cách nào để tôi có thể xây dựng một mô hình để phân biệt các tweet về Apple (Inc.) với các tweet về táo (trái cây)?


85

Xem bên dưới để biết 50 tweet về "apple". Tôi đã tự tay gắn nhãn các kết quả phù hợp tích cực về Apple Inc. Chúng được đánh dấu là 1 bên dưới.

Dưới đây là một vài dòng:

1|“@chrisgilmer: Apple targets big business with new iOS 7 features http://bit.ly/15F9JeF ”. Finally.. A corp iTunes account!
0|“@Zach_Paull: When did green skittles change from lime to green apple? #notafan” @Skittles
1|@dtfcdvEric: @MaroneyFan11 apple inc is searching for people to help and tryout all their upcoming tablet within our own net page No.
0|@STFUTimothy have you tried apple pie shine?
1|#SuryaRay #India Microsoft to bring Xbox and PC games to Apple, Android phones: Report: Microsoft Corp... http://dlvr.it/3YvbQx  @SuryaRay

Đây là tập dữ liệu tổng thể: http://pastebin.com/eJuEb4eB

Tôi cần xây dựng một mô hình phân loại "Apple" (Inc). từ phần còn lại.

Tôi không tìm kiếm tổng quan chung về học máy, thay vào đó tôi đang tìm kiếm mô hình thực tế trong mã ( ưu tiên Python ).


18
Về cơ bản bạn muốn điều này: en.wikipedia.org/wiki/Bayesian_spam_filtering
Eddi

1
Bạn gắn nhãn dữ liệu của mình bằng tay, nhưng muốn các thư viện có quy mô đó. Điều này được giám sát hay không được giám sát?
dan

1
Eddi, cảm ơn, vì nhận xét. Xem email lọc thư thực sự đã giúp một cái gì đó kích thích trong não tôi. Tôi đã có thể nhìn thấy một ví dụ thực tế về những gì tôi đang cố gắng làm, chỉ là áp dụng theo cách khác.
SAL

5
Nhận dạng đối tượng được đặt tên: nlp.stanford.edu/software/CRF-NER.shtml .
Neil McGuigan

1
@NeilMcGuigan hấp dẫn. Tôi đã dán một số văn bản vào bản demo của họ ( nlp.stanford.edu:8080/ner/process ) và rất ấn tượng với cách các mô hình khác nhau phân loại các từ.
Ryan

Câu trả lời:


39

Tôi sẽ làm điều đó như sau:

  1. Chia câu thành các từ, chuẩn hóa chúng, xây dựng từ điển
  2. Với mỗi từ, hãy lưu trữ số lần chúng xuất hiện trong các tweet về công ty và số lần chúng xuất hiện trong các tweet về trái cây - những tweet này phải được xác nhận bởi một con người
  3. Khi một tweet mới xuất hiện, hãy tìm mọi từ trong tweet trong từ điển, tính điểm trọng số - những từ được sử dụng thường xuyên liên quan đến công ty sẽ nhận được điểm công ty cao và ngược lại; những từ hiếm khi được sử dụng, hoặc được sử dụng với cả công ty và trái cây, sẽ không có nhiều điểm.

2
Cảm ơn bạn đã trả lời của bạn về điều này. Câu trả lời của bạn kết hợp với nhận xét ở trên thực sự đã giúp tôi tìm ra giải pháp. Bạn có thể giúp tôi trau dồi giải pháp này?
SAL

10
Đây là một mô tả không chính thức về phân loại Bayes.
sanityinc

1
Tôi thích "thực hiện pseudo-code phân loại Bayes" :)
AMADANON Inc.

73

Những gì bạn đang tìm kiếm được gọi là Nhận dạng đối tượng được đặt tên . Đây là một kỹ thuật thống kê (phổ biến nhất) sử dụng Trường ngẫu nhiên có điều kiện để tìm các thực thể được đặt tên, dựa trên việc đã được đào tạo để tìm hiểu những điều về các thực thể được đặt tên.

Về cơ bản, nó xem xét nội dung và ngữ cảnh của từ, (nhìn lại và chuyển tiếp một vài từ), để ước tính xác suất từ ​​đó là một thực thể được đặt tên.

Phần mềm tốt có thể xem xét các đặc điểm khác của từ, chẳng hạn như độ dài hoặc hình dạng của chúng (như "Vcv" nếu nó bắt đầu bằng "Nguyên âm-phụ âm-nguyên âm")

Một thư viện rất tốt (GPL) là NER của Stanford

Đây là bản demo: http://nlp.stanford.edu:8080/ner/

Một số văn bản mẫu để thử:

Tôi đang ăn một quả táo tại trụ sở Apple và tôi nghĩ về Apple Martin, con gái của anh chàng Coldplay

(các bộ phân loại 3 lớp và 4 lớp hiểu đúng)


5
Điều đó thực sự thú vị. Có thể xem mã cho english.conll.4class.distsim.crf.ser.gz? Tôi muốn xem cách một người xây dựng một cái gì đó như thế này.
Ryan

Mã cho NER là mã nguồn mở, nhưng dữ liệu mà họ sử dụng trong hội nghị CONLL thì không. Tuy nhiên, bạn có thể tìm thấy Reuters Corpus trực tuyến tại NIST.
Neil McGuigan,

31

Tôi có một hệ thống bán làm việc để giải quyết vấn đề này, có nguồn mở bằng cách sử dụng scikit-learning, với một loạt các bài đăng trên blog mô tả những gì tôi đang làm. Vấn đề tôi đang giải quyết là sự phân biệt theo nghĩa từ (chọn một trong nhiều tùy chọn nghĩa của từ ), không giống như Nhận dạng đối tượng được đặt tên. Cách tiếp cận cơ bản của tôi có phần cạnh tranh với các giải pháp hiện có và (quan trọng là) có thể tùy chỉnh.

Có một số công cụ NER thương mại hiện có (OpenCalais, DBPedia Spotlight và AlchemyAPI) có thể cung cấp cho bạn một kết quả thương mại đủ tốt - hãy thử những công cụ này trước!

Tôi đã sử dụng một số trong số này cho một dự án khách hàng (tôi tham khảo ý kiến ​​sử dụng NLP / ML ở London), nhưng tôi không hài lòng với việc thu hồi của chúng ( độ chính xác và thu hồi ). Về cơ bản, họ có thể chính xác (khi họ nói "Đây là Apple Inc" thì họ thường đúng), nhưng với khả năng thu hồi thấp (họ hiếm khi nói "Đây là Apple Inc" mặc dù đối với một người, tweet rõ ràng là về Apple Inc). Tôi nghĩ rằng đó sẽ là một bài tập thú vị về mặt trí tuệ để xây dựng một phiên bản mã nguồn mở phù hợp với các tweet. Đây là mã hiện tại: https://github.com/ianozsvald/social_media_brand_disambiguator

Tôi sẽ lưu ý - tôi không cố gắng giải quyết vấn đề phân định từ theo nghĩa khái quát bằng cách tiếp cận này, chỉ định hướng thương hiệu (công ty, con người, v.v.) khi bạn đã có tên của họ. Đó là lý do tại sao tôi tin rằng cách tiếp cận đơn giản này sẽ hiệu quả.

Tôi đã bắt đầu điều này sáu tuần trước, và nó được viết bằng Python 2.7 sử dụng scikit-learning. Nó sử dụng một cách tiếp cận rất cơ bản. Tôi vectơ hóa bằng công cụ vectơ đếm số nhị phân (tôi chỉ đếm xem một từ có xuất hiện hay không chứ không phải bao nhiêu lần) với 1-3  n-gam . Tôi không mở rộng quy mô với TF-IDF (TF-IDF tốt khi bạn có độ dài tài liệu thay đổi; đối với tôi, các tweet chỉ có một hoặc hai câu và kết quả thử nghiệm của tôi không cho thấy sự cải thiện với TF-IDF).

Tôi sử dụng tokenizer cơ bản rất cơ bản nhưng hữu ích một cách đáng ngạc nhiên. Nó bỏ qua @ # (vì vậy bạn sẽ mất một số ngữ cảnh) và tất nhiên không mở rộng URL. Sau đó, tôi đào tạo bằng cách sử dụng hồi quy logistic , và có vẻ như vấn đề này hơi có thể phân tách tuyến tính (rất nhiều thuật ngữ cho một lớp không tồn tại cho lớp kia). Hiện tại, tôi đang tránh bất kỳ việc cắt gốc / làm sạch nào (Tôi đang thử Điều đơn giản nhất có thể mà có thể làm được).

Mã có README đầy đủ và bạn sẽ có thể nhập các tweet của mình tương đối dễ dàng và sau đó làm theo các đề xuất của tôi để thử nghiệm.

Điều này có hiệu quả với Apple vì mọi người không ăn hoặc uống máy tính của Apple, cũng như chúng ta không gõ hoặc chơi với trái cây, vì vậy các từ dễ dàng bị chia thành loại này hay loại khác. Điều kiện này có thể không được giữ khi xem xét điều gì đó như #definance cho chương trình truyền hình (nơi mọi người cũng sử dụng #definance liên quan đến Mùa xuân Ả Rập, các trận đấu cricket, ôn tập kỳ thi và một ban nhạc). Các phương pháp tiếp cận thông minh hơn có thể được yêu cầu ở đây.

Tôi có một loạt các bài đăng trên blog mô tả dự án này bao gồm một bài thuyết trình kéo dài một giờ mà tôi đã trình bày tại nhóm người dùng BrightonPython (đã biến thành một bài thuyết trình ngắn hơn cho 140 người tại DataScienceLondon).

Nếu bạn sử dụng một cái gì đó như LogisticRegression (nơi bạn nhận được xác suất cho mỗi phân loại), bạn chỉ có thể chọn các phân loại đáng tin cậy và theo cách đó bạn có thể tạo ra độ chính xác cao bằng cách giao dịch với thu hồi (để bạn nhận được kết quả chính xác, nhưng ít kết quả hơn). Bạn sẽ phải điều chỉnh điều này cho hệ thống của mình.

Đây là một cách tiếp cận thuật toán khả thi sử dụng scikit-learning:

  • Sử dụng Binary CountVectorizer (Tôi không nghĩ rằng số từ trong các tin nhắn ngắn thêm nhiều thông tin vì hầu hết các từ chỉ xuất hiện một lần)
  • Bắt đầu với bộ phân loại Cây Quyết định. Nó sẽ có hiệu suất có thể giải thích được (xem Overfitting với Cây Quyết định để làm ví dụ).
  • Chuyển sang hồi quy logistic
  • Điều tra các lỗi được tạo ra bởi các bộ phân loại (đọc kết quả được xuất của DecisionTree hoặc xem các hệ số trong LogisticRegression, xử lý các tweet bị phân loại sai trở lại thông qua Vectorizer để xem biểu diễn Bag of Words bên dưới trông như thế nào - sẽ có ít mã thông báo hơn ở đó bạn đã bắt đầu bằng tweet thô - có đủ để phân loại không?)
  • Xem mã ví dụ của tôi trong https://github.com/ianozsvald/social_media_brand_disambiguator/blob/master/learn1.py để biết phiên bản hoạt động của phương pháp này

Những điều cần cân nhắc:

  • Bạn cần một tập dữ liệu lớn hơn. Tôi đang sử dụng 2000 tweet được gắn nhãn (tôi mất năm giờ) và tối thiểu bạn muốn có một bộ cân bằng với> 100 cho mỗi lớp (xem ghi chú trang bị quá mức bên dưới)
  • Cải thiện trình mã hóa (rất dễ dàng với scikit-learning) để giữ # @ trong mã thông báo và có thể thêm bộ phát hiện thương hiệu viết hoa (như ghi chú của người dùng @ user2425429)
  • Hãy xem xét một bộ phân loại phi tuyến tính (như gợi ý của @ oiez ở trên) khi mọi thứ trở nên khó khăn hơn. Cá nhân tôi thấy LinearSVC làm tệ hơn hồi quy logistic (nhưng điều đó có thể là do không gian tính năng chiều cao mà tôi vẫn chưa giảm).
  • Một phần cụ thể của tweet của trình gắn thẻ giọng nói (theo ý kiến ​​khiêm tốn của tôi không phải của Standford như @Neil gợi ý - nó hoạt động kém trên Twitter kém ngữ pháp theo kinh nghiệm của tôi)
  • Khi bạn có nhiều mã thông báo, bạn có thể muốn thực hiện một số giảm kích thước (Tôi chưa thử điều này - hãy xem bài đăng trên blog của tôi về hình phạt LogisticRegression l1 l2)

Re. quá sức. Trong tập dữ liệu của tôi với 2000 mục, tôi có một ảnh chụp nhanh 10 phút từ Twitter về các tweet của 'quả táo'. Khoảng 2/3 số tweet dành cho Apple Inc, 1/3 dành cho các mục đích sử dụng táo khác. Tôi lấy ra một tập hợp con cân bằng (tôi nghĩ là khoảng 584 hàng) của mỗi lớp và thực hiện xác nhận chéo năm lần để đào tạo.

Vì tôi chỉ có khoảng thời gian 10 phút nên tôi có nhiều tweet về cùng một chủ đề và đây có lẽ là lý do tại sao trình phân loại của tôi hoạt động rất tốt so với các công cụ hiện có - nó sẽ quá phù hợp với các tính năng đào tạo mà không tổng quát tốt (trong khi quảng cáo hiện có các công cụ hoạt động kém hơn trên snapshop này, nhưng đáng tin cậy hơn trên một tập hợp dữ liệu rộng hơn). Tôi sẽ mở rộng cửa sổ thời gian của mình để kiểm tra điều này như một phần công việc tiếp theo.


Tôi không vui khi xem qua mã của bạn và cố gắng sao chép / mô phỏng / đào tạo, nhưng tôi nợ bạn một lời xin lỗi vì đã không trao toàn bộ 50pts tiền thưởng. Tôi đã rời SO vào cuối tuần qua và đã bỏ lỡ thời hạn trao giải. Rất may, cộng đồng SO đã tham gia và thấy phù hợp để trao cho bạn 25 điểm.
Ryan

1
Không thành vấn đề :-) Mã, README và các bài đăng trên blog sẽ cung cấp cho bạn ý tưởng về cách tiếp cận của tôi. Nó là cố tình đơn giản nhưng có vẻ để làm việc Ok.
Ian Ozsvald

12

Bạn có thể làm như sau:

  1. Viết chính tả các từ có chứa số lần xuất hiện của chúng trong các tweet liên quan đến trái cây và công ty. Điều này có thể đạt được bằng cách cung cấp cho nó một số tweet mẫu có độ nghiêng mà chúng tôi biết.

  2. Sử dụng đủ dữ liệu trước đó, chúng tôi có thể tìm ra xác suất của một từ xuất hiện trong tweet về apple inc.

  3. Nhân xác suất của từng từ để có xác suất của toàn bộ tweet.

Một ví dụ đơn giản:

p_f = Xác suất của tweet trái cây.

p_w_f = Xác suất một từ xuất hiện trong tweet trái cây.

p_t_f = Xác suất tổng hợp của tất cả các từ trong tweet xảy ra một tweet trái cây = p_w1_f * p_w2_f * ...

p_f_t = Xác suất trái cây đưa ra một tweet cụ thể.

p_c, p_w_c, p_t_c, p_c_t là các giá trị tương ứng của công ty.

Một giá trị 1 mượt mà hơn laplacian được thêm vào để loại bỏ vấn đề về tần suất xuất hiện của các từ mới không có trong cơ sở dữ liệu của chúng tôi.

old_tweets = {'apple pie sweet potatoe cake baby https://vine.co/v/hzBaWVA3IE3': '0', ...}
known_words = {}
total_company_tweets = total_fruit_tweets =total_company_words = total_fruit_words = 0

for tweet in old_tweets:
    company = old_tweets[tweet]
    for word in tweet.lower().split(" "):
        if not word in known_words:
            known_words[word] = {"company":0, "fruit":0 }
        if company == "1":
            known_words[word]["company"] += 1
            total_company_words += 1
        else:
            known_words[word]["fruit"] += 1
            total_fruit_words += 1

    if company == "1":
        total_company_tweets += 1
    else:
        total_fruit_tweets += 1
total_tweets = len(old_tweets)

def predict_tweet(new_tweet,K=1):
    p_f = (total_fruit_tweets+K)/(total_tweets+K*2)
    p_c = (total_company_tweets+K)/(total_tweets+K*2)
    new_words = new_tweet.lower().split(" ")

    p_t_f = p_t_c = 1
    for word in new_words:
        try:
            wordFound = known_words[word]
        except KeyError:
            wordFound = {'fruit':0,'company':0}
        p_w_f = (wordFound['fruit']+K)/(total_fruit_words+K*(len(known_words)))
        p_w_c = (wordFound['company']+K)/(total_company_words+K*(len(known_words)))
    p_t_f *= p_w_f
    p_t_c *= p_w_c

    #Applying bayes rule
    p_f_t = p_f * p_t_f/(p_t_f*p_f + p_t_c*p_c)
    p_c_t = p_c * p_t_c/(p_t_f*p_f + p_t_c*p_c)
    if p_c_t > p_f_t:
        return "Company"
    return "Fruit"

9

Nếu bạn không gặp sự cố khi sử dụng thư viện bên ngoài, tôi khuyên bạn nên dùng scikit-learning vì nó có thể làm việc này tốt hơn và nhanh hơn bất cứ thứ gì bạn có thể tự viết mã. Tôi chỉ muốn làm một cái gì đó như thế này:

Xây dựng kho dữ liệu của bạn. Tôi đã tìm hiểu danh sách để rõ ràng hơn, nhưng tùy thuộc vào cách dữ liệu của bạn được lưu trữ, bạn có thể cần thực hiện những việc khác nhau:

def corpus_builder(apple_inc_tweets, apple_fruit_tweets):
    corpus = [tweet for tweet in apple_inc_tweets] + [tweet for tweet in apple_fruit_tweets]
    labels = [1 for x in xrange(len(apple_inc_tweets))] + [0 for x in xrange(len(apple_fruit_tweets))]
    return (corpus, labels)

Điều quan trọng là bạn sẽ có hai danh sách giống như sau:

([['apple inc tweet i love ios and iphones'], ['apple iphones are great'], ['apple fruit tweet i love pie'], ['apple pie is great']], [1, 1, 0, 0])

[1, 1, 0, 0] đại diện cho các nhãn âm và dương.

Sau đó, bạn tạo một Đường ống! Pipeline là một lớp học scikit giúp dễ dàng xâu chuỗi các bước xử lý văn bản lại với nhau, do đó bạn chỉ phải gọi một đối tượng khi đào tạo / dự đoán:

def train(corpus, labels)
    pipe = Pipeline([('vect', CountVectorizer(ngram_range=(1, 3), stop_words='english')),
                        ('tfidf', TfidfTransformer(norm='l2')),
                        ('clf', LinearSVC()),])
    pipe.fit_transform(corpus, labels)
    return pipe

Bên trong Pipeline có ba bước xử lý. CountVectorizer mã hóa các từ, chia nhỏ, đếm và chuyển dữ liệu thành một ma trận thưa thớt. TfidfTransformer là tùy chọn và bạn có thể muốn xóa nó tùy thuộc vào xếp hạng độ chính xác (thực hiện các bài kiểm tra xác thực chéo và tìm kiếm lưới cho các thông số tốt nhất có một chút liên quan, vì vậy tôi sẽ không giải thích ở đây). LinearSVC là một thuật toán phân loại văn bản tiêu chuẩn.

Cuối cùng, bạn dự đoán loại tweet:

def predict(pipe, tweet):
    prediction = pipe.predict([tweet])
    return prediction

Một lần nữa, tweet cần phải nằm trong danh sách, vì vậy tôi giả định rằng nó đang nhập hàm dưới dạng chuỗi.

Đặt tất cả những thứ đó vào một lớp hoặc bất cứ thứ gì, và bạn đã hoàn thành. Ít nhất, với ví dụ rất cơ bản này.

Tôi đã không kiểm tra mã này nên nó có thể không hoạt động nếu bạn chỉ sao chép-dán, nhưng nếu bạn muốn sử dụng scikit-learning, nó sẽ cung cấp cho bạn ý tưởng về nơi bắt đầu.

EDIT: đã cố gắng giải thích các bước chi tiết hơn.


6

Sử dụng cây quyết định dường như hoạt động khá tốt cho vấn đề này. Ít nhất nó tạo ra độ chính xác cao hơn một trình phân loại bayes ngây thơ với các tính năng đã chọn của tôi.

Nếu bạn muốn thử một số khả năng, bạn có thể sử dụng mã sau, mã này yêu cầu cài đặt nltk. Sách nltk cũng được cung cấp miễn phí trực tuyến, vì vậy bạn có thể muốn đọc một chút về cách tất cả những thứ này thực sự hoạt động: http://nltk.googlecode.com/svn/trunk/doc/book/ch06.html

#coding: utf-8
import nltk
import random
import re

def get_split_sets():
    structured_dataset = get_dataset()
    train_set = set(random.sample(structured_dataset, int(len(structured_dataset) * 0.7)))
    test_set = [x for x in structured_dataset if x not in train_set]

    train_set = [(tweet_features(x[1]), x[0]) for x in train_set]
    test_set = [(tweet_features(x[1]), x[0]) for x in test_set]
    return (train_set, test_set)

def check_accurracy(times=5):
    s = 0
    for _ in xrange(times):
        train_set, test_set = get_split_sets()
        c = nltk.classify.DecisionTreeClassifier.train(train_set)
        # Uncomment to use a naive bayes classifier instead
        #c = nltk.classify.NaiveBayesClassifier.train(train_set)
        s += nltk.classify.accuracy(c, test_set)

    return s / times


def remove_urls(tweet):
    tweet = re.sub(r'http:\/\/[^ ]+', "", tweet)
    tweet = re.sub(r'pic.twitter.com/[^ ]+', "", tweet)
    return tweet

def tweet_features(tweet):
    words = [x for x in nltk.tokenize.wordpunct_tokenize(remove_urls(tweet.lower())) if x.isalpha()]
    features = dict()
    for bigram in nltk.bigrams(words):
        features["hasBigram(%s)" % ",".join(bigram)] = True
    for trigram in nltk.trigrams(words):
        features["hasTrigram(%s)" % ",".join(trigram)] = True  
    return features

def get_dataset():
    dataset = """copy dataset in here
"""
    structured_dataset = [('fruit' if x[0] == '0' else 'company', x[2:]) for x in dataset.splitlines()]
    return structured_dataset

if __name__ == '__main__':
    print check_accurracy()

1
Cái này hoạt động ra sao? Tôi không thấy "tính năng đã chọn" của bạn trong mã của bạn. Nó có tự động chọn các tính năng dựa trên tập huấn luyện không? Hay nó được lưu trữ ở dict()một nơi khác? Tôi nghĩ nếu tập huấn luyện của một người đủ lớn, thì chẳng lẽ máy tính không thể tự tìm ra các tính năng sao? (không được giám sát?)
Ryan

2
Các tính năng được trích xuất bằng cách sử dụng hàm tweet_features. Về cơ bản, nó loại bỏ các url khỏi các tweet, và sau đó tạo ra một feature dict có các mục đọc như 'hasBigram (foo, bar)' = True.
Paul Dubs

1
Vậy 'hasBigram(foo,bar)' = Truechuỗi tweet bao gồm những foo barđâu? Vì vậy, nó xây dựng bigrams và bát quái cho mỗi tweet và gắn cờ nó trong tính năng tích cực dict()? Do đó, với tweet, "alpha beta gamma delta"nó sẽ xây dựng các biểu tượng dict () cho alpha,beta; beta,gamma; and gamma,delta;và bát quái cho alpha,beta,gammabeta,gamma,delta? Và từ số bi và tri gam dương và âm đã cho, bộ phân loại bộ phân loại quyết định hay bộ phân loại bayes có thể làm được điều kỳ diệu của họ?
Ryan

2
Chính xác. Khi sử dụng trình phân loại bayes, bạn cũng có thể nhận được các tính năng hữu ích nhất bằng cách gọi "show_most_informative_features ()" trên đó.
Paul Dubs

Paul, tôi đã xây dựng một phiên bản php thô của cái này và bạn hoàn toàn chính xác. Đây là một cách siêu hiệu quả để xây dựng một từ điển có trọng số. Tôi nghĩ điều này có thể dễ dàng mở rộng quy mô mà không cần phải tạo tất cả các từ khóa theo cách thủ công. Tôi mong muốn tìm hiểu thêm về cách thực hiện điều này bên trong thư viện học máy tiêu chuẩn.
Ryan

5

Cảm ơn bạn cho các ý kiến ​​cho đến nay. Đây là một giải pháp làm việc mà tôi đã chuẩn bị với PHP. Tôi vẫn muốn nghe từ những người khác một cách tiếp cận thuật toán hơn cho cùng một giải pháp này.

<?php

// Confusion Matrix Init
$tp = 0;
$fp = 0;
$fn = 0;
$tn = 0;
$arrFP = array();
$arrFN = array();

// Load All Tweets to string
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, 'http://pastebin.com/raw.php?i=m6pP8ctM');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
$strCorpus = curl_exec($ch);
curl_close($ch);

// Load Tweets as Array
$arrCorpus = explode("\n", $strCorpus);
foreach ($arrCorpus as $k => $v) {
    // init
    $blnActualClass = substr($v,0,1);
    $strTweet = trim(substr($v,2));

    // Score Tweet
    $intScore = score($strTweet);

    // Build Confusion Matrix and Log False Positives & Negatives for Review
    if ($intScore > 0) {
        if ($blnActualClass == 1) {
            // True Positive
            $tp++;
        } else {
            // False Positive
            $fp++;
            $arrFP[] = $strTweet;
        }
    } else {
        if ($blnActualClass == 1) {
            // False Negative
            $fn++;
            $arrFN[] = $strTweet;
        } else {
            // True Negative
            $tn++;
        }
    }
}

// Confusion Matrix and Logging
echo "
           Predicted
            1     0
Actual 1   $tp     $fp
Actual 0    $fn    $tn

";

if (count($arrFP) > 0) {
    echo "\n\nFalse Positives\n";
    foreach ($arrFP as $strTweet) {
        echo "$strTweet\n";
    }
}

if (count($arrFN) > 0) {
    echo "\n\nFalse Negatives\n";
    foreach ($arrFN as $strTweet) {
        echo "$strTweet\n";
    }
}

function LoadDictionaryArray() {
    $strDictionary = <<<EOD
10|iTunes
10|ios 7
10|ios7
10|iPhone
10|apple inc
10|apple corp
10|apple.com
10|MacBook
10|desk top
10|desktop
1|config
1|facebook
1|snapchat
1|intel
1|investor
1|news
1|labs
1|gadget
1|apple store
1|microsoft
1|android
1|bonds
1|Corp.tax
1|macs
-1|pie
-1|clientes
-1|green apple
-1|banana
-10|apple pie
EOD;

    $arrDictionary = explode("\n", $strDictionary);
    foreach ($arrDictionary as $k => $v) {
        $arr = explode('|', $v);
        $arrDictionary[$k] = array('value' => $arr[0], 'term' => strtolower(trim($arr[1])));
    }
    return $arrDictionary;
}

function score($str) {
    $str = strtolower($str);
    $intScore = 0;
    foreach (LoadDictionaryArray() as $arrDictionaryItem) {
        if (strpos($str,$arrDictionaryItem['term']) !== false) {
            $intScore += $arrDictionaryItem['value'];
        }
    }
    return $intScore;
}
?>

Các kết quả trên:

           Predicted
            1     0
Actual 1   31     1
Actual 0    1    17


False Positives
1|Royals apple #ASGame @mlb @ News Corp Building http://instagram.com/p/bBzzgMrrIV/


False Negatives
-1|RT @MaxFreixenet: Apple no tiene clientes. Tiene FANS// error.... PAGAS por productos y apps, ergo: ERES CLIENTE.

4

Trong tất cả các ví dụ mà bạn đã đưa ra, Apple (inc) hoặc được gọi là A pple hoặc apple inc , vì vậy một cách khả thi có thể là tìm kiếm:

  • viết hoa "A" trong Apple

  • một "inc" sau quả táo

  • các từ / cụm từ như "OS", "hệ điều hành", "Mac", "iPhone", ...

  • hoặc sự kết hợp của chúng


1
Trong hàm, tôi đã thực hiện một strtolower để lọc ra các chữ cái viết hoa. Một chút thô thiển, nhưng nó đã hoạt động.
SAL

@SAL Tôi không mong đợi nó sẽ rất hữu ích, nhưng nếu bạn có một thời hạn, sau đó ...
user2425429

4

Để đơn giản hóa các câu trả lời dựa trên Trường ngẫu nhiên có điều kiện một chút ... ngữ cảnh ở đây rất lớn. Bạn sẽ muốn chọn những dòng tweet thể hiện rõ ràng Apple là công ty so với quả táo. Hãy để tôi phác thảo danh sách các tính năng ở đây có thể hữu ích cho bạn khi bắt đầu. Để biết thêm thông tin, hãy tra cứu cụm từ danh từ và một thứ gọi là nhãn BIO. Xem ( http://www.cis.upenn.edu/~pereira/papers/crf.pdf )

Các từ bao quanh: Xây dựng một vectơ đặc điểm cho từ trước và từ tiếp theo hoặc nếu bạn muốn có thêm các đặc trưng có thể là 2 từ trước và 2 từ tiếp theo. Bạn không muốn có quá nhiều từ trong mô hình hoặc nó sẽ không khớp với dữ liệu cho lắm. Trong Xử lý ngôn ngữ tự nhiên, bạn sẽ muốn giữ điều này càng chung chung càng tốt.

Các tính năng khác để nhận được từ các từ xung quanh bao gồm:

Ký tự đầu tiên có phải là viết hoa hay không

Ký tự cuối cùng trong từ có phải là dấu chấm hay không

Phần lời nói của từ (Tra cứu phần gắn thẻ lời nói)

Bản thân văn bản của từ

Tôi không khuyên điều này, nhưng để cung cấp thêm ví dụ về các tính năng dành riêng cho Apple:

WordIs (Apple)

NextWordIs (Inc.)

Bạn sẽ có được điểm. Hãy coi Nhận dạng đối tượng được đặt tên giống như mô tả một chuỗi, sau đó sử dụng một số phép toán để cho máy tính biết cách tính toán đó.

Hãy nhớ rằng xử lý ngôn ngữ tự nhiên là một hệ thống dựa trên đường ống. Thông thường, bạn chia nhỏ mọi thứ thành câu, chuyển sang mã hóa, sau đó thực hiện một phần của việc gắn thẻ giọng nói hoặc thậm chí phân tích cú pháp phụ thuộc.

Tất cả là để cung cấp cho bạn danh sách các tính năng bạn có thể sử dụng trong mô hình của mình để xác định những gì bạn đang tìm kiếm.


3

Có một thư viện thực sự tốt để xử lý văn bản ngôn ngữ tự nhiên bằng Python được gọi là nltk. Bạn nên xem qua.

Một chiến lược bạn có thể thử là nhìn vào n-gram (nhóm từ) có từ "apple" trong đó. Một số từ có nhiều khả năng được sử dụng bên cạnh "apple" khi nói về trái cây, những từ khác khi nói về công ty và bạn có thể sử dụng những từ đó để phân loại các tweet.


1
Cảm ơn Manetheran. Tôi không phải là người đăng ban đầu, nhưng tôi cũng quan tâm đến câu trả lời. Đối với tiền thưởng, tôi đang tìm kiếm một số mã (thậm chí đang sử dụng nltk) có thể giúp tôi bắt đầu đúng hướng với nhiệm vụ học máy "chào thế giới". Apple (bao gồm) và táo (trái cây) có vẻ như là một nhiệm vụ hoàn hảo.
Ryan

3

Sử dụng LibShortText . Đây Python tiện ích đã được điều chỉnh để làm việc cho các công việc phân loại văn bản ngắn, và nó hoạt động tốt. Tối đa bạn sẽ phải làm là viết một vòng lặp để chọn ra sự kết hợp tốt nhất của các cờ. Tôi đã sử dụng nó để phân loại hành vi lời nói được giám sát trong email và kết quả chính xác lên đến 95-97% (trong quá trình xác thực chéo 5 lần!).

Và nó đến từ các nhà sản xuất LIBSVMLIBLINEAR có việc triển khai máy vectơ hỗ trợ (SVM) được sử dụng trong sklearn và cran, vì vậy bạn có thể hoàn toàn yên tâm rằng việc triển khai của chúng không có lỗi.


2

Tạo bộ lọc AI để phân biệt Apple Inc (công ty) với táo (trái cây). Vì đây là các tweet, hãy xác định tập huấn luyện của bạn với một vectơ gồm 140 trường, mỗi trường là ký tự được viết trong tweet ở vị trí X (0 đến 139). Nếu tweet ngắn hơn, chỉ cần cung cấp giá trị trống.

Sau đó, xây dựng một tập hợp đào tạo đủ lớn để có được độ chính xác tốt (tùy theo sở thích của bạn). Chỉ định một giá trị kết quả cho mỗi tweet, một tweet của Apple Inc nhận được 1 (đúng) và một tweet táo (trái cây) nhận được 0. Đây sẽ là một trường hợp học có giám sát trong hồi quy logistic .

Đó là học máy, thường dễ viết mã hơn và hoạt động tốt hơn. Nó phải học hỏi từ bộ bạn cung cấp cho nó, và nó không được mã hóa cứng.

Tôi không biết Python , vì vậy tôi không thể viết mã cho nó, nhưng nếu bạn muốn dành nhiều thời gian hơn cho logic và lý thuyết của máy học, bạn có thể muốn xem lớp học mà tôi đang theo dõi.

Hãy thử khóa học Machine Learning của Coursera do Andrew Ng . Bạn sẽ học máy học trên MATLAB hoặc Octave , nhưng khi bạn đã nắm được kiến ​​thức cơ bản, bạn sẽ có thể viết máy học bằng bất kỳ ngôn ngữ nào nếu bạn hiểu phép toán đơn giản (đơn giản trong hồi quy logistic).

Có nghĩa là, việc nhận mã từ ai đó sẽ không khiến bạn không thể hiểu những gì diễn ra trong mã máy học. Bạn có thể muốn đầu tư vài giờ cho chủ đề này để xem điều gì đang thực sự diễn ra.


Cảm ơn Fawar. Tôi đã hy vọng một số mã trên "hello world" cho mục đích chính xác này - để tìm hiểu cách ML hoạt động. Tôi sẽ tra cứu lớp mặc dù. Có vẻ tốt.
Ryan

0

Tôi khuyên bạn nên tránh các câu trả lời đề xuất nhận dạng thực thể. Bởi vì tác vụ này là phân loại văn bản đầu tiên và thứ hai là nhận dạng đối tượng (bạn có thể thực hiện mà không cần nhận dạng đối tượng).

Tôi nghĩ con đường dẫn đến kết quả nhanh nhất sẽ là spacy + thần đồng . Spacy đã suy nghĩ rất kỹ về mô hình cho ngôn ngữ tiếng Anh, vì vậy bạn không cần phải xây dựng mô hình của riêng mình. Trong khi thần đồng cho phép nhanh chóng tạo tập dữ liệu đào tạo và tinh chỉnh mô hình spacy cho nhu cầu của bạn.

Đủ mẫu thì 1 ngày nữa là có mẫu nha.


Đồng thời, spaCynerthành phần đường ống, nó sẽ không có lợi cho việc phân loại này? Tôi cho rằng mô hình của họ có thể nhận ra Apple(vì đây là một trong những công ty lớn nhất và nổi tiếng nhất trên thế giới) tốt hơn nhiều so với một mô hình mà bạn có thể đưa ra trong một ngày.
Szymon Maszke

@Szymon: NER có thể giúp được hoặc không. Theo tôi hiểu, bạn muốn sử dụng các thực thể được đặt tên (thực tế là chúng hiện diện trong văn bản) để làm đặc điểm cho nhiệm vụ phân loại chính. Rõ ràng, NER sẽ không có độ chính xác 100% vì có mức độ mơ hồ cao. Vì vậy, mô hình phân loại chính sẽ quyết định nó sẽ tin tưởng vào tính năng này trong những trường hợp nào. Có thể (tôi nghĩ rất có thể) rằng một mô hình phân loại cơ bản sẽ cho kết quả của mô hình NER rất thấp. Và điều này có nghĩa là bạn sẽ dành thời gian cho NER, thứ (gần như) không được sử dụng.
Dim

Không phải ý tôi. Chỉ cần tạo spacy.Doctừ mỗi văn bản, lặp lại các NER của chúng với doc.entsvà kiểm tra xem có NER nào có .textthuộc tính bằng Apple. Thực tế thú vị, ví dụ đầu tiên của họ bao gồm Apple.
Szymon Maszke

Và nếu ai đó muốn tạo một mô hình, nó có lẽ sẽ liên quan đến RNN / CNN và những thứ tương tự, điều chỉnh chúng cho phù hợp, tìm kiến ​​trúc, loại ô, v.v., tôi không nghĩ rằng các mô hình dễ dàng hơn sẽ xử lý tốt việc phân định và bối cảnh. Tại sao lại làm cho cuộc sống của bạn trở nên dễ dàng hơn (trừ khi bạn muốn học một điều gì đó trên đường đi), nếu ai đó đã làm điều đó cho bạn?
Szymon Maszke

@SzymonMaszke mô hình của bạn phức tạp hơn và khó đào tạo hơn. Để mô hình của bạn hoạt động cho mục đích đã đề cập, bạn không chỉ phải tìm một NE mà còn phải tìm nó ở một nơi chính xác (mã thông báo). Với mô hình phân loại mà tôi đề nghị bạn nên tối ưu hóa mô hình cho mục tiêu cốt lõi của mình - xác định đó là công ty Apple hay quả Táo. Điều đó dễ đào tạo hơn và do đó rất có thể nó sẽ chính xác hơn.
Dim
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.