Cách thực hiện phân tích cảm xúc trong Python 3 bằng Bộ công cụ ngôn ngữ tự nhiên (NLTK)
Một lượng lớn dữ liệu được tạo ngày nay là không có cấu trúc , đòi hỏi phải xử lý để tạo ra thông tin chi tiết. Một số ví dụ về dữ liệu phi cấu trúc là các bài báo, bài đăng trên mạng xã hội và lịch sử tìm kiếm. Quá trình phân tích ngôn ngữ tự nhiên và hiểu ngôn ngữ tự nhiên thuộc lĩnh vực Xử lý ngôn ngữ tự nhiên (NLP). Phân tích tình cảm là một nhiệm vụ NLP phổ biến, bao gồm việc phân loại các văn bản hoặc các phần của văn bản thành một tình cảm được định nghĩa . Bạn sẽ sử dụng Bộ công cụ ngôn ngữ tự nhiên (NLTK) , một thư viện NLP thường được sử dụng trong Python, để phân tích dữ liệu dạng văn bản.Trong hướng dẫn này, bạn sẽ chuẩn bị một tập dữ liệu gồm các tweet mẫu từ gói NLTK cho NLP với các phương pháp làm sạch dữ liệu khác nhau. Khi tập dữ liệu đã sẵn sàng để xử lý, bạn sẽ đào tạo một mô hình về các tweet đã được phân loại trước và sử dụng mô hình này để phân loại các tweet mẫu thành các tình cảm tiêu cực và tích cực.
Bài viết này giả định bạn đã quen thuộc với những kiến thức cơ bản về Python (xem loạt bài Cách viết mã trong Python 3 của ta ), chủ yếu là việc sử dụng cấu trúc dữ liệu, lớp và phương thức. Hướng dẫn giả định bạn không có kiến thức nền tảng về NLP và nltk
, mặc dù một số kiến thức về nó là một lợi thế bổ sung.
Yêu cầu
- Hướng dẫn này dựa trên version Python 3.6.5. Nếu bạn chưa cài đặt Python 3, Đây là hướng dẫn cài đặt và cài đặt môi trường lập trình local cho Python 3 .
- Nên làm quen với dữ liệu ngôn ngữ. Nếu bạn mới sử dụng NLTK, hãy xem Hướng dẫn Cách làm việc với Dữ liệu Ngôn ngữ trong Python 3 bằng hướng dẫn Bộ công cụ Ngôn ngữ Tự nhiên (NLTK) .
Bước 1 - Cài đặt NLTK và Download Dữ liệu
Bạn sẽ sử dụng gói NLTK bằng Python cho tất cả các việc NLP trong hướng dẫn này. Trong bước này, bạn sẽ cài đặt NLTK và download các tweet mẫu mà bạn sẽ sử dụng để đào tạo và kiểm tra mô hình của bạn .
Trước tiên, hãy cài đặt gói NLTK với trình quản lý gói pip
:
- pip install nltk==3.3
Hướng dẫn này sẽ sử dụng các tweet mẫu là một phần của gói NLTK. Đầu tiên, hãy bắt đầu một phiên tương tác Python bằng cách chạy lệnh sau:
- python3
Sau đó, nhập mô- nltk
trong trình thông dịch python.
- import nltk
Download các tweet mẫu từ gói NLTK:
- nltk.download('twitter_samples')
Chạy lệnh này từ trình thông dịch Python download và lưu trữ local các tweet. Khi các mẫu được download , chúng sẽ có sẵn để bạn sử dụng.
Bạn sẽ sử dụng các tweet tiêu cực và tích cực để đào tạo mô hình của bạn về phân tích cảm xúc trong phần sau của hướng dẫn. Các tweet không có cảm xúc sẽ được sử dụng để kiểm tra mô hình của bạn.
Nếu bạn muốn sử dụng tập dữ liệu của riêng mình, bạn có thể thu thập các tweet từ một khoảng thời gian cụ thể, user hoặc thẻ bắt đầu bằng # bằng cách sử dụng API Twitter .
Đến đây bạn đã nhập NLTK và download các tweet mẫu, hãy thoát phiên tương tác bằng lệnh vào exit()
. Bạn đã sẵn sàng nhập các tweet và bắt đầu xử lý dữ liệu.
Bước 2 - Mã hóa dữ liệu
Máy tính không thể xử lý chính xác ngôn ngữ ở dạng ban đầu, vì vậy bạn cần xử lý ngôn ngữ để máy dễ hiểu hơn. Phần đầu tiên của việc hiểu dữ liệu là thông qua một quá trình được gọi là mã hóa hoặc chia các chuỗi thành các phần nhỏ hơn được gọi là mã thông báo .
Mã thông báo là một chuỗi các ký tự trong văn bản đóng role như một đơn vị. Dựa trên cách bạn tạo mã thông báo, chúng có thể bao gồm các từ, biểu tượng cảm xúc, thẻ bắt đầu bằng #, liên kết hoặc thậm chí các ký tự riêng lẻ. Một cách cơ bản để chia ngôn ngữ thành mã thông báo là tách văn bản dựa trên khoảng trắng và dấu câu.
Để bắt đầu, hãy tạo một file .py
mới để chứa tập lệnh của bạn. Hướng dẫn này sẽ sử dụng nlp_test.py
:
- nano nlp_test.py
Trong file này, trước tiên bạn sẽ nhập twitter_samples
để bạn có thể làm việc với dữ liệu đó:
from nltk.corpus import twitter_samples
Thao tác này sẽ nhập ba tập dữ liệu từ NLTK chứa các tweet khác nhau để đào tạo và kiểm tra mô hình:
-
negative_tweets.json
: 5000 tweet với tình cảm tiêu cực -
positive_tweets.json
: 5000 tweet với tình cảm tích cực -
tweets.20150430-223406.json
: 20000 tweet không có cảm xúc
Tiếp theo, tạo các biến cho positive_tweets
, negative_tweets
và text
:
from nltk.corpus import twitter_samples positive_tweets = twitter_samples.strings('positive_tweets.json') negative_tweets = twitter_samples.strings('negative_tweets.json') text = twitter_samples.strings('tweets.20150430-223406.json')
Phương thức strings()
của twitter_samples
sẽ in tất cả các tweet trong tập dữ liệu dưới dạng chuỗi. Đặt các bộ sưu tập tweet khác nhau làm biến sẽ giúp xử lý và kiểm tra dễ dàng hơn.
Trước khi sử dụng tokenizer trong NLTK, bạn cần download một tài nguyên bổ sung, punkt
. Mô-đun punkt
là một mô hình được đào tạo trước giúp bạn mã hóa các từ và câu. Ví dụ, mô hình này biết rằng tên có thể chứa một dấu chấm (như “S. Daityari”) và sự hiện diện của dấu chấm này trong một câu không nhất thiết phải kết thúc nó. Đầu tiên, hãy bắt đầu một phiên tương tác Python:
- python3
Chạy các lệnh sau trong phiên để download tài nguyên punkt
:
- import nltk
- nltk.download('punkt')
Sau khi quá trình download hoàn tất, bạn đã sẵn sàng sử dụng các bộ phân bổ của NLTK. NLTK cung cấp trình mã hóa mặc định cho các tweet bằng phương thức .tokenized()
. Thêm một dòng để tạo một đối tượng mã hóa tập dữ liệu positive_tweets.json
:
from nltk.corpus import twitter_samples positive_tweets = twitter_samples.strings('positive_tweets.json') negative_tweets = twitter_samples.strings('negative_tweets.json') text = twitter_samples.strings('tweets.20150430-223406.json') tweet_tokens = twitter_samples.tokenized('positive_tweets.json')
Nếu bạn muốn kiểm tra tập lệnh để xem phương thức .tokenized
đang hoạt động, hãy thêm nội dung được đánh dấu vào tập lệnh nlp_test.py
của bạn. Điều này sẽ mã hóa một tweet duy nhất từ tập dữ liệu positive_tweets.json
:
from nltk.corpus import twitter_samples positive_tweets = twitter_samples.strings('positive_tweets.json') negative_tweets = twitter_samples.strings('negative_tweets.json') text = twitter_samples.strings('tweets.20150430-223406.json') tweet_tokens = twitter_samples.tokenized('positive_tweets.json')[0] print(tweet_tokens[0])
Lưu file cũng như chạy tập lệnh:
- python3 nlp_test.py
Quá trình mã hóa mất một thời gian vì nó không phải là một sự phân chia đơn giản trên khoảng trắng. Sau một vài giây xử lý, bạn sẽ thấy như sau:
Output['#FollowFriday', '@France_Inte', '@PKuchly57', '@Milipol_Paris', 'for', 'being', 'top', 'engaged', 'members', 'in', 'my', 'community', 'this', 'week', ':)']
Ở đây, phương thức .tokenized()
trả về các ký tự đặc biệt như @
và _
. Các ký tự này sẽ bị xóa thông qua các biểu thức chính quy ở phần sau của hướng dẫn này.
Đến đây bạn đã thấy phương thức .tokenized()
hoạt động như thế nào, hãy đảm bảo comment hoặc xóa dòng cuối cùng để in tweet được mã hóa khỏi tập lệnh bằng cách thêm dấu #
vào đầu dòng:
from nltk.corpus import twitter_samples positive_tweets = twitter_samples.strings('positive_tweets.json') negative_tweets = twitter_samples.strings('negative_tweets.json') text = twitter_samples.strings('tweets.20150430-223406.json') tweet_tokens = twitter_samples.tokenized('positive_tweets.json')[0] #print(tweet_tokens[0])
Tập lệnh của bạn hiện đã được cấu hình để mã hóa dữ liệu. Trong bước tiếp theo, bạn sẽ cập nhật tập lệnh để chuẩn hóa dữ liệu.
Bước 3 - Chuẩn hóa dữ liệu
Các từ có các dạng khác nhau — ví dụ, “ran”, “running” và “running” là các dạng khác nhau của cùng một động từ, “run”. Tùy thuộc vào yêu cầu phân tích của bạn, tất cả các version này có thể cần được chuyển đổi sang cùng một dạng, "chạy". Chuẩn hóa trong NLP là quá trình chuyển đổi một từ sang dạng chuẩn của nó.
Chuẩn hóa giúp group các từ có cùng nghĩa nhưng khác hình thức lại với nhau. Nếu không chuẩn hóa, “ran”, “running” và “running” sẽ được coi là các từ khác nhau, mặc dù bạn có thể cần chúng được coi là cùng một từ. Trong phần này, bạn khám phá việc tạo gốc và lemmatization , là hai kỹ thuật chuẩn hóa phổ biến.
Stemming là một quá trình loại bỏ các phụ tố khỏi một từ. Bắt đầu, chỉ làm việc với các dạng động từ đơn giản, là một quá trình tự khám phá loại bỏ các phần cuối của từ.
Trong hướng dẫn này, bạn sẽ sử dụng quá trình lemmatization, bình thường hóa một từ với ngữ cảnh của từ vựng và phân tích hình thái của các từ trong văn bản. Thuật toán lemmatization phân tích cấu trúc của từ và ngữ cảnh của nó để chuyển nó sang dạng chuẩn hóa. Do đó, nó phải trả giá bằng tốc độ. So sánh root và lemmatization cuối cùng đi đến sự đánh đổi giữa tốc độ và độ chính xác.
Trước khi bạn tiếp tục sử dụng lemmatization, hãy download các tài nguyên cần thiết bằng lệnh thông tin sau vào phiên tương tác Python:
- python3
Chạy các lệnh sau trong phiên để download các tài nguyên:
- import nltk
- nltk.download('wordnet')
- nltk.download('averaged_perceptron_tagger')
wordnet
là một database từ vựng cho ngôn ngữ tiếng Anh giúp tập lệnh xác định từ cơ sở. Bạn cần tài nguyên averaged_perceptron_tagger
để xác định ngữ cảnh của một từ trong câu.
Sau khi download , bạn gần như đã sẵn sàng để sử dụng lemmatizer. Trước khi chạy lemmatizer, bạn cần xác định ngữ cảnh cho từng từ trong văn bản của bạn . Điều này đạt được nhờ thuật toán gắn thẻ, thuật toán này đánh giá vị trí tương đối của một từ trong câu. Trong một phiên Python, Nhập hàm pos_tag
và cung cấp danh sách các mã thông báo làm đối số để nhận các thẻ. Hãy để ta thử điều này bằng Python:
- from nltk.tag import pos_tag
- from nltk.corpus import twitter_samples
-
- tweet_tokens = twitter_samples.tokenized('positive_tweets.json')
- print(pos_tag(tweet_tokens[0]))
Đây là kết quả của hàm pos_tag
.
Output[('#FollowFriday', 'JJ'), ('@France_Inte', 'NNP'), ('@PKuchly57', 'NNP'), ('@Milipol_Paris', 'NNP'), ('for', 'IN'), ('being', 'VBG'), ('top', 'JJ'), ('engaged', 'VBN'), ('members', 'NNS'), ('in', 'IN'), ('my', 'PRP$'), ('community', 'NN'), ('this', 'DT'), ('week', 'NN'), (':)', 'NN')]
Từ danh sách các thẻ, đây là danh sách các mục phổ biến nhất và ý nghĩa của chúng:
-
NNP
: Danh từ riêng, số ít -
NN
: Danh từ, chung, số ít hoặc dung lượng -
IN
: Giới từ hoặc kết hợp, phụ -
VBG
: Động từ, động từ hoặc hiện tại phân từ -
VBN
: Động từ, quá khứ phân từ
Đây là danh sách đầy đủ của tập dữ liệu .
Nói chung, nếu một thẻ bắt đầu bằng NN
, từ đó là danh từ và nếu nó bắt đầu bằng VB
, từ đó là động từ. Sau khi xem xét các thẻ, hãy thoát khỏi phiên Python bằng lệnh exit()
.
Để kết hợp điều này vào một chức năng chuẩn hóa một câu, trước tiên bạn nên tạo các thẻ cho mỗi mã thông báo trong văn bản, sau đó bổ sung từng từ bằng cách sử dụng thẻ.
Cập nhật file nlp_test.py
với hàm sau làm sai câu:
... from nltk.tag import pos_tag from nltk.stem.wordnet import WordNetLemmatizer def lemmatize_sentence(tokens): lemmatizer = WordNetLemmatizer() lemmatized_sentence = [] for word, tag in pos_tag(tokens): if tag.startswith('NN'): pos = 'n' elif tag.startswith('VB'): pos = 'v' else: pos = 'a' lemmatized_sentence.append(lemmatizer.lemmatize(word, pos)) return lemmatized_sentence print(lemmatize_sentence(tweet_tokens[0]))
Mã này nhập lớp WordNetLemmatizer
và khởi tạo nó thành một biến, lemmatizer
.
lemmatize_sentence
tiên, hàm lemmatize_sentence
lấy thẻ vị trí của mỗi mã thông báo của một tweet. Trong if
tuyên bố, nếu thẻ bắt đầu với NN
, token được gán như một danh từ. Tương tự, nếu thẻ bắt đầu bằng VB
, thì mã thông báo được chỉ định như một động từ.
Lưu file cũng như chạy tập lệnh:
- python3 nlp_test.py
Đây là kết quả :
Output['#FollowFriday', '@France_Inte', '@PKuchly57', '@Milipol_Paris', 'for', 'be', 'top', 'engage', 'member', 'in', 'my', 'community', 'this', 'week', ':)']
Bạn sẽ nhận thấy rằng động từ being
chuyển sang dạng root , be
, và các members
danh từ chuyển member
. Trước khi bạn tiếp tục, hãy comment dòng cuối cùng in tweet mẫu từ script.
Đến đây bạn đã tạo thành công một hàm để chuẩn hóa các từ, bạn đã sẵn sàng để chuyển sang loại bỏ nhiễu.
Bước 4 - Loại bỏ tiếng ồn khỏi dữ liệu
Trong bước này, bạn sẽ loại bỏ nhiễu khỏi tập dữ liệu. Nhiễu là bất kỳ phần nào của văn bản không thêm ý nghĩa hoặc thông tin vào dữ liệu.
Tiếng ồn là đặc trưng cho từng dự án, vì vậy những gì tạo nên tiếng ồn trong một dự án có thể không có trong một dự án khác. Ví dụ, các từ phổ biến nhất trong một ngôn ngữ được gọi là các từ dừng . Một số ví dụ về các từ dừng là “is”, “the” và “a”. Chúng thường không liên quan khi xử lý ngôn ngữ, trừ khi một trường hợp sử dụng cụ thể đảm bảo việc đưa chúng vào.
Trong hướng dẫn này, bạn sẽ sử dụng các biểu thức chính quy trong Python để tìm kiếm và xóa các mục sau:
- Siêu liên kết - Tất cả các siêu liên kết trong Twitter đều được chuyển đổi thành công cụ rút gọn URL t.co. Do đó, giữ chúng trong quá trình xử lý văn bản sẽ không thêm bất kỳ giá trị nào cho phân tích.
- Twitter xử lý các câu trả lời - Những tên user Twitter này được đặt trước bằng ký hiệu
@
, không truyền tải bất kỳ ý nghĩa nào. - Dấu câu và ký tự đặc biệt - Mặc dù những ký tự này thường cung cấp ngữ cảnh cho dữ liệu văn bản, nhưng ngữ cảnh này thường khó xử lý. Để đơn giản, bạn sẽ xóa tất cả các dấu câu và ký tự đặc biệt khỏi tweet.
Để xóa siêu liên kết, trước tiên bạn cần tìm kiếm một chuỗi con trùng với URL bắt đầu bằng http://
hoặc https://
, tiếp theo là các chữ cái, số hoặc ký tự đặc biệt. Sau khi một mẫu được khớp, phương thức .sub()
sẽ thay thế nó bằng một chuỗi trống.
Vì ta sẽ chuẩn hóa các dạng từ trong hàm remove_noise()
, bạn có thể comment về lemmatize_sentence()
từ script.
Thêm mã sau vào file nlp_test.py
của bạn để loại bỏ nhiễu khỏi tập dữ liệu:
... import re, string def remove_noise(tweet_tokens, stop_words = ()): cleaned_tokens = [] for token, tag in pos_tag(tweet_tokens): token = re.sub('http[s]?://(?:[a-zA-Z]|[0-9]|[$-_@.&+#]|[!*\(\),]|'\ '(?:%[0-9a-fA-F][0-9a-fA-F]))+','', token) token = re.sub("(@[A-Za-z0-9_]+)","", token) if tag.startswith("NN"): pos = 'n' elif tag.startswith('VB'): pos = 'v' else: pos = 'a' lemmatizer = WordNetLemmatizer() token = lemmatizer.lemmatize(token, pos) if len(token) > 0 and token not in string.punctuation and token.lower() not in stop_words: cleaned_tokens.append(token.lower()) return cleaned_tokens
Đoạn mã này tạo ra một remove_noise()
để loại bỏ nhiễu và kết hợp chuẩn hóa và lemmatization đã đề cập trong phần trước. Mã có hai đối số: mã thông báo tweet và nhiều từ dừng.
Sau đó, mã sử dụng một vòng lặp để loại bỏ nhiễu khỏi tập dữ liệu. Để xóa siêu liên kết, trước tiên, mã tìm kiếm một chuỗi con phù hợp với URL bắt đầu bằng http://
hoặc https://
, tiếp theo là các chữ cái, số hoặc ký tự đặc biệt. Sau khi một mẫu được khớp, phương thức .sub()
sẽ thay thế nó bằng một chuỗi trống hoặc ''
.
Tương tự, để xóa @
đề cập, mã thay thế phần có liên quan của văn bản bằng cách sử dụng biểu thức chính quy. Mã sử dụng thư viện re
để tìm kiếm các ký hiệu @
, theo sau là số, chữ cái hoặc _
và thay thế chúng bằng một chuỗi trống.
Cuối cùng, bạn có thể xóa dấu câu bằng string
thư viện.
Ngoài ra, bạn cũng sẽ xóa các từ dừng bằng cách sử dụng tập hợp các từ dừng được tích hợp sẵn trong NLTK, cần được download riêng.
Thực thi lệnh sau từ một phiên tương tác Python để download tài nguyên này:
- nltk.download('stopwords')
Khi tài nguyên được download , hãy thoát phiên tương tác.
Bạn có thể sử dụng phương thức .words()
để nhận danh sách các từ dừng bằng tiếng Anh. Để kiểm tra chức năng, hãy để ta chạy nó trên tweet mẫu của ta . Thêm các dòng sau vào cuối file nlp_test.py
:
... from nltk.corpus import stopwords stop_words = stopwords.words('english') print(remove_noise(tweet_tokens[0], stop_words))
Sau khi lưu file , hãy chạy lại tập lệnh để nhận kết quả tương tự như sau:
Output['#followfriday', 'top', 'engage', 'member', 'community', 'week', ':)']
Lưu ý hàm loại bỏ tất cả đề cập @
, dừng từ và chuyển các từ thành chữ thường.
Trước khi tiếp tục bài tập mô hình hóa trong bước tiếp theo, hãy sử dụng hàm remove_noise()
để làm sạch các tweet tích cực và tiêu cực. Comment dòng để in kết quả của remove_noise()
trên tweet mẫu và thêm phần sau vào tập lệnh nlp_test.py
:
... from nltk.corpus import stopwords stop_words = stopwords.words('english') #print(remove_noise(tweet_tokens[0], stop_words)) positive_tweet_tokens = twitter_samples.tokenized('positive_tweets.json') negative_tweet_tokens = twitter_samples.tokenized('negative_tweets.json') positive_cleaned_tokens_list = [] negative_cleaned_tokens_list = [] for tokens in positive_tweet_tokens: positive_cleaned_tokens_list.append(remove_noise(tokens, stop_words)) for tokens in negative_tweet_tokens: negative_cleaned_tokens_list.append(remove_noise(tokens, stop_words))
Đến đây bạn đã thêm mã để làm sạch các tweet mẫu, bạn có thể cần so sánh các mã thông báo ban đầu với các mã thông báo đã được làm sạch cho một tweet mẫu. Nếu bạn muốn kiểm tra điều này, hãy thêm mã sau vào file để so sánh cả hai version của tweet thứ 500 trong danh sách:
... print(positive_tweet_tokens[500]) print(positive_cleaned_tokens_list[500])
Lưu file và chạy tập lệnh. Từ kết quả , bạn sẽ thấy rằng dấu câu và liên kết đã bị loại bỏ, và các từ đã được chuyển đổi thành chữ thường.
Output['Dang', 'that', 'is', 'some', 'rad', '@AbzuGame', '#fanart', '!', ':D', 'https://t.co/bI8k8tb9ht'] ['dang', 'rad', '#fanart', ':d']
Có một số vấn đề nhất định có thể phát sinh trong quá trình xử lý trước văn bản. Ví dụ: các từ không có dấu cách (“iLoveYou”) sẽ được coi là một và có thể khó tách các từ như vậy. Hơn nữa, “Hi”, “Hii” và “Hiiiii” sẽ được kịch bản xử lý khác nhau trừ khi bạn viết một cái gì đó cụ thể để giải quyết vấn đề. Việc tinh chỉnh quá trình loại bỏ nhiễu cho dữ liệu cụ thể của bạn là điều thường thấy.
Đến đây bạn đã thấy hàm remove_noise()
hoạt động, hãy nhớ comment hoặc xóa hai dòng cuối cùng khỏi tập lệnh để bạn có thể thêm vào nó:
... #print(positive_tweet_tokens[500]) #print(positive_cleaned_tokens_list[500])
Trong bước này, bạn đã loại bỏ nhiễu khỏi dữ liệu để phân tích hiệu quả hơn. Trong bước tiếp theo, bạn sẽ phân tích dữ liệu để tìm những từ phổ biến nhất trong tập dữ liệu mẫu của bạn .
Bước 5 - Xác định mật độ từ
Hình thức cơ bản nhất của phân tích dữ liệu văn bản là lấy ra tần số từ. Một tweet duy nhất là quá nhỏ của một thực thể để tìm ra sự phân bố của các từ, do đó, việc phân tích tần suất của các từ sẽ được thực hiện trên tất cả các tweet tích cực.
Đoạn mã sau định nghĩa một hàm trình tạo , có tên get_all_words
, lấy danh sách các tweet làm đối số để cung cấp danh sách các từ trong tất cả các mã thông báo tweet đã tham gia. Thêm mã sau vào file nlp_test.py
của bạn:
... def get_all_words(cleaned_tokens_list): for tokens in cleaned_tokens_list: for token in tokens: yield token all_pos_words = get_all_words(positive_cleaned_tokens_list)
Đến đây bạn đã tổng hợp tất cả các từ trong mẫu tweet, bạn có thể tìm ra những từ phổ biến nhất bằng cách sử dụng lớp FreqDist
của NLTK. Thêm mã sau vào file nlp_test.py
:
from nltk import FreqDist freq_dist_pos = FreqDist(all_pos_words) print(freq_dist_pos.most_common(10))
Phương thức .most_common()
liệt kê các từ xuất hiện thường xuyên nhất trong dữ liệu. Lưu file sau khi thực hiện những thay đổi này.
Khi bạn chạy file ngay bây giờ, bạn sẽ tìm thấy các thuật ngữ phổ biến nhất trong dữ liệu:
Output[(':)', 3691), (':-)', 701), (':d', 658), ('thanks', 388), ('follow', 357), ('love', 333), ('...', 290), ('good', 283), ('get', 263), ('thank', 253)]
Từ dữ liệu này, bạn có thể thấy rằng các thực thể biểu tượng cảm xúc tạo thành một số phần phổ biến nhất của các tweet tích cực. Trước khi tiếp tục bước tiếp theo, hãy đảm bảo bạn comment dòng cuối cùng của tập lệnh in ra mười mã thông báo hàng đầu.
Tóm lại, bạn đã extract các tweet từ nltk
, mã hóa, chuẩn hóa và làm sạch các tweet để sử dụng trong mô hình. Cuối cùng, bạn cũng đã xem xét tần số của các mã thông báo trong dữ liệu và kiểm tra tần suất của mười mã thông báo hàng đầu.
Trong bước tiếp theo, bạn sẽ chuẩn bị dữ liệu để phân tích tình cảm.
Bước 6 - Chuẩn bị dữ liệu cho mô hình
Phân tích tình cảm là một quá trình xác định thái độ của tác giả về một chủ đề được viết về. Bạn sẽ tạo một tập dữ liệu đào tạo để đào tạo một mô hình. Đây là một quá trình học máy học có giám sát, đòi hỏi bạn phải liên kết từng tập dữ liệu với một “tình cảm” để đào tạo. Trong hướng dẫn này, mô hình của bạn sẽ sử dụng cảm xúc "tích cực" và "tiêu cực".
Phân tích tình cảm được dùng để phân loại văn bản thành nhiều loại tình cảm. Để đơn giản và khả dụng của tập dữ liệu đào tạo, hướng dẫn này giúp bạn đào tạo mô hình của bạn chỉ trong hai danh mục, tích cực và tiêu cực.
Mô hình là một mô tả của một hệ thống sử dụng các luật và phương trình. Nó có thể đơn giản như một phương trình dự đoán cân nặng của một người, dựa trên chiều cao của họ. Một mô hình phân tích tình cảm mà bạn sẽ xây dựng sẽ liên kết các tweet với một tình cảm tích cực hoặc tiêu cực. Bạn cần chia tập dữ liệu của bạn thành hai phần. Mục đích của phần đầu tiên là xây dựng mô hình, trong khi phần tiếp theo kiểm tra hiệu suất của mô hình.
Trong bước chuẩn bị dữ liệu, bạn sẽ chuẩn bị dữ liệu để phân tích tình cảm bằng cách chuyển đổi mã thông báo sang dạng từ điển và sau đó chia nhỏ dữ liệu cho mục đích đào tạo và thử nghiệm.
Chuyển đổi mã thông báo thành từ điển
Đầu tiên, bạn sẽ chuẩn bị dữ liệu để đưa vào mô hình. Bạn sẽ sử dụng bộ phân loại Naive Bayes trong NLTK để thực hiện bài tập mô hình hóa. Lưu ý mô hình không chỉ yêu cầu danh sách các từ trong một tweet mà còn yêu cầu một từ điển Python với các từ là khóa và True
là giá trị. Hàm sau đây tạo chức năng tạo để thay đổi định dạng của dữ liệu đã được làm sạch.
Thêm mã sau đây để chuyển đổi các tweet từ danh sách các mã thông báo đã được làm sạch thành từ điển với các khóa là mã thông báo và True
dưới dạng giá trị. Các từ điển tương ứng được lưu trữ trong positive_tokens_for_model
và negative_tokens_for_model
.
... def get_tweets_for_model(cleaned_tokens_list): for tweet_tokens in cleaned_tokens_list: yield dict([token, True] for token in tweet_tokens) positive_tokens_for_model = get_tweets_for_model(positive_cleaned_tokens_list) negative_tokens_for_model = get_tweets_for_model(negative_cleaned_tokens_list)
Tách tập dữ liệu để đào tạo và kiểm tra mô hình
Tiếp theo, bạn cần chuẩn bị dữ liệu để đào tạo NaiveBayesClassifier
. Thêm mã sau vào file để chuẩn bị dữ liệu:
... import random positive_dataset = [(tweet_dict, "Positive") for tweet_dict in positive_tokens_for_model] negative_dataset = [(tweet_dict, "Negative") for tweet_dict in negative_tokens_for_model] dataset = positive_dataset + negative_dataset random.shuffle(dataset) train_data = dataset[:7000] test_data = dataset[7000:]
Mã này gắn nhãn Positive
hoặc Negative
cho mỗi tweet. Sau đó, nó tạo ra một dataset
bằng cách kết hợp các tweet tích cực và tiêu cực.
Theo mặc định, dữ liệu chứa tất cả các tweet tích cực, theo sau là tất cả các tweet tiêu cực theo thứ tự. Khi đào tạo mô hình, bạn nên cung cấp một mẫu dữ liệu của bạn không chứa bất kỳ sai lệch nào. Để tránh sai lệch, bạn đã thêm mã để sắp xếp dữ liệu một cách ngẫu nhiên bằng cách sử dụng phương thức .shuffle()
random
.
Cuối cùng, mã chia dữ liệu xáo trộn thành tỷ lệ 70:30 để đào tạo và thử nghiệm, tương ứng. Vì số lượng tweet là 10000, bạn có thể sử dụng 7000 tweet đầu tiên từ tập dữ liệu xáo trộn để đào tạo mô hình và 3000 tweet cuối cùng để kiểm tra mô hình.
Trong bước này, bạn đã chuyển đổi các mã thông báo đã được làm sạch sang dạng từ điển, xáo trộn ngẫu nhiên tập dữ liệu và chia nó thành dữ liệu đào tạo và thử nghiệm.
Bước 7 - Xây dựng và thử nghiệm mô hình
Cuối cùng, bạn có thể sử dụng NaiveBayesClassifier
để xây dựng mô hình. Sử dụng phương thức .train()
để huấn luyện mô hình và phương thức .accuracy()
để kiểm tra mô hình trên dữ liệu thử nghiệm.
... from nltk import classify from nltk import NaiveBayesClassifier classifier = NaiveBayesClassifier.train(train_data) print("Accuracy is:", classify.accuracy(classifier, test_data)) print(classifier.show_most_informative_features(10))
Lưu, đóng và thực thi file sau khi thêm mã. Đầu ra của mã sẽ như sau:
OutputAccuracy is: 0.9956666666666667 Most Informative Features :( = True Negati : Positi = 2085.6 : 1.0 :) = True Positi : Negati = 986.0 : 1.0 welcome = True Positi : Negati = 37.2 : 1.0 arrive = True Positi : Negati = 31.3 : 1.0 sad = True Negati : Positi = 25.9 : 1.0 follower = True Positi : Negati = 21.1 : 1.0 bam = True Positi : Negati = 20.7 : 1.0 glad = True Positi : Negati = 18.1 : 1.0 x15 = True Negati : Positi = 15.9 : 1.0 community = True Positi : Negati = 14.1 : 1.0
Độ chính xác được định nghĩa là tỷ lệ phần trăm tweet trong tập dữ liệu thử nghiệm mà mô hình có thể dự đoán chính xác cảm xúc. Độ chính xác 99,5% trên bộ thử nghiệm là khá tốt.
Trong bảng hiển thị các tính năng nhiều thông tin nhất, mỗi hàng trong kết quả hiển thị tỷ lệ xuất hiện của mã thông báo trong các tweet được gắn thẻ tích cực và tiêu cực trong tập dữ liệu đào tạo. Hàng đầu tiên trong dữ liệu biểu thị rằng trong tất cả các tweet có chứa mã thông báo :(
, tỷ lệ giữa các tweet phủ định và tích cực là 2085.6
trên 1
Thật thú vị, có vẻ như có một mã thông báo với :(
trong tập dữ liệu tích cực. Bạn có thể thấy rằng Hai mục phân biệt hàng đầu trong văn bản là biểu tượng cảm xúc. Hơn nữa, những từ như sad
dẫn đến cảm xúc tiêu cực, trong khi welcome
và glad
được liên kết với cảm xúc tích cực.
Tiếp theo, bạn có thể kiểm tra cách mô hình hoạt động trên các tweet ngẫu nhiên từ Twitter. Thêm mã này vào file :
... from nltk.tokenize import word_tokenize custom_tweet = "I ordered just once from TerribleCo, they screwed up, never used the app again." custom_tokens = remove_noise(word_tokenize(custom_tweet)) print(classifier.classify(dict([token, True] for token in custom_tokens)))
Mã này sẽ cho phép bạn kiểm tra các tweet tùy chỉnh bằng cách cập nhật chuỗi được liên kết với biến custom_tweet
. Lưu file sau khi thực hiện những thay đổi này.
Chạy tập lệnh để phân tích văn bản tùy chỉnh. Đây là kết quả cho văn bản tùy chỉnh trong ví dụ:
Output'Negative'
Bạn cũng có thể kiểm tra xem nó có mô tả đúng các tweet tích cực hay không:
... custom_tweet = 'Congrats #SportStar on your 7th best goal from last season winning goal of the year :) #Baller #Topbin #oneofmanyworldies'
Đây là kết quả :
Output'Positive'
Đến đây bạn đã kiểm tra cả tình cảm tích cực và tiêu cực, hãy cập nhật biến số để kiểm tra tình cảm phức tạp hơn như mỉa mai.
... custom_tweet = 'Thank you for sending my baggage to CityX and flying me to CityY at the same time. Brilliant service. #thanksGenericAirline'
Đây là kết quả :
Output'Positive'
Mô hình đã phân loại ví dụ này là tích cực. Điều này là do dữ liệu đào tạo không đủ toàn diện để phân loại các tweet châm biếm là tiêu cực. Trong trường hợp bạn muốn mô hình của bạn dự đoán chế nhạo, bạn cần cung cấp đủ lượng dữ liệu đào tạo để đào tạo nó cho phù hợp.
Trong bước này, bạn đã xây dựng và kiểm tra mô hình. Bạn cũng đã khám phá ra một số hạn chế của nó, chẳng hạn như không phát hiện ra sự mỉa mai trong các ví dụ cụ thể. Mã đã hoàn thành của bạn vẫn còn sót lại phần tạo tác sau khi làm theo hướng dẫn, vì vậy bước tiếp theo sẽ hướng dẫn bạn căn chỉnh mã theo các phương pháp hay nhất của Python.
Bước 8 - Xóa mã (Tùy chọn)
Mặc dù bạn đã hoàn thành hướng dẫn, bạn nên tổ chức lại mã trong file nlp_test.py
để tuân theo các phương pháp lập trình tốt nhất. Theo phương pháp hay nhất, mã của bạn phải đáp ứng tiêu chí sau:
- Tất cả các lần nhập phải ở đầu file . Các bản nhập từ cùng một thư viện nên được group lại với nhau trong một câu lệnh.
- Tất cả các chức năng phải được xác định sau khi nhập.
- Tất cả các câu lệnh trong file phải được đặt trong điều kiện
if __name__ == "__main__":
Điều này đảm bảo các câu lệnh không được thực thi nếu bạn đang nhập các chức năng của file trong một file khác.
Ta cũng sẽ xóa mã đã được comment theo hướng dẫn, cùng với hàm lemmatize_sentence
, vì quá trình lemmatization được hoàn thành bởi hàm remove_noise
mới.
Đây là version đã được làm sạch của nlp_test.py
:
from nltk.stem.wordnet import WordNetLemmatizer from nltk.corpus import twitter_samples, stopwords from nltk.tag import pos_tag from nltk.tokenize import word_tokenize from nltk import FreqDist, classify, NaiveBayesClassifier import re, string, random def remove_noise(tweet_tokens, stop_words = ()): cleaned_tokens = [] for token, tag in pos_tag(tweet_tokens): token = re.sub('http[s]?://(?:[a-zA-Z]|[0-9]|[$-_@.&+#]|[!*\(\),]|'\ '(?:%[0-9a-fA-F][0-9a-fA-F]))+','', token) token = re.sub("(@[A-Za-z0-9_]+)","", token) if tag.startswith("NN"): pos = 'n' elif tag.startswith('VB'): pos = 'v' else: pos = 'a' lemmatizer = WordNetLemmatizer() token = lemmatizer.lemmatize(token, pos) if len(token) > 0 and token not in string.punctuation and token.lower() not in stop_words: cleaned_tokens.append(token.lower()) return cleaned_tokens def get_all_words(cleaned_tokens_list): for tokens in cleaned_tokens_list: for token in tokens: yield token def get_tweets_for_model(cleaned_tokens_list): for tweet_tokens in cleaned_tokens_list: yield dict([token, True] for token in tweet_tokens) if __name__ == "__main__": positive_tweets = twitter_samples.strings('positive_tweets.json') negative_tweets = twitter_samples.strings('negative_tweets.json') text = twitter_samples.strings('tweets.20150430-223406.json') tweet_tokens = twitter_samples.tokenized('positive_tweets.json')[0] stop_words = stopwords.words('english') positive_tweet_tokens = twitter_samples.tokenized('positive_tweets.json') negative_tweet_tokens = twitter_samples.tokenized('negative_tweets.json') positive_cleaned_tokens_list = [] negative_cleaned_tokens_list = [] for tokens in positive_tweet_tokens: positive_cleaned_tokens_list.append(remove_noise(tokens, stop_words)) for tokens in negative_tweet_tokens: negative_cleaned_tokens_list.append(remove_noise(tokens, stop_words)) all_pos_words = get_all_words(positive_cleaned_tokens_list) freq_dist_pos = FreqDist(all_pos_words) print(freq_dist_pos.most_common(10)) positive_tokens_for_model = get_tweets_for_model(positive_cleaned_tokens_list) negative_tokens_for_model = get_tweets_for_model(negative_cleaned_tokens_list) positive_dataset = [(tweet_dict, "Positive") for tweet_dict in positive_tokens_for_model] negative_dataset = [(tweet_dict, "Negative") for tweet_dict in negative_tokens_for_model] dataset = positive_dataset + negative_dataset random.shuffle(dataset) train_data = dataset[:7000] test_data = dataset[7000:] classifier = NaiveBayesClassifier.train(train_data) print("Accuracy is:", classify.accuracy(classifier, test_data)) print(classifier.show_most_informative_features(10)) custom_tweet = "I ordered just once from TerribleCo, they screwed up, never used the app again." custom_tokens = remove_noise(word_tokenize(custom_tweet)) print(custom_tweet, classifier.classify(dict([token, True] for token in custom_tokens)))
Kết luận
Hướng dẫn này đã giới thiệu cho bạn mô hình phân tích tình cảm cơ bản bằng cách sử dụng thư viện nltk
trong Python 3. Đầu tiên, bạn thực hiện xử lý trước trên các tweet bằng cách mã hóa một tweet, chuẩn hóa các từ và loại bỏ tạp âm. Tiếp theo, bạn hình dung các mục thường xuyên xuất hiện trong dữ liệu. Cuối cùng, bạn đã xây dựng một mô hình để liên kết các tweet với một tình cảm cụ thể.
Mô hình học tập có giám sát chỉ tốt như dữ liệu đào tạo của nó. Để tăng cường hơn nữa mô hình, bạn có thể cân nhắc thêm nhiều danh mục khác như phấn khích và tức giận. Trong hướng dẫn này, bạn chỉ mới làm xước bề mặt bằng cách xây dựng một mô hình thô sơ. Dưới đây là hướng dẫn chi tiết về các cân nhắc khác nhau mà người ta phải quan tâm khi thực hiện phân tích tình cảm.
Các tin liên quan
Cách thiết lập một sổ ghi chép Jupyter với Python 3 trên Debian 102019-08-29
Cách cài đặt Python 3 và thiết lập môi trường lập trình cục bộ trên macOS
2019-08-16
Cách cài đặt Python 3 và thiết lập môi trường lập trình cục bộ trên macOS
2019-08-16
Cách cài đặt Python 3 và thiết lập môi trường lập trình cục bộ trên macOS
2019-08-16
Cách cài đặt Python 3 và thiết lập môi trường lập trình trên Debian 10
2019-08-05
Cách cài đặt bản phân phối Python Anaconda trên Debian 10
2019-07-09
Cách cài đặt Phân phối Python Anaconda trên Ubuntu 18.04
2019-04-18
Cách áp dụng thị giác máy tính để xây dựng bộ lọc chó dựa trên cảm xúc trong Python 3
2019-04-03
Cách phát hiện và trích xuất khuôn mặt từ một image bằng OpenCV và Python
2019-03-27
Cách tạo bộ phân loại học máy bằng Python với Scikit-learning
2019-03-24