주석이 부족한 부분이 있으면 말해주세요.
import csv
import re
import nltk
import collections
import matplotlib.pyplot as plt
# https://github.com/e9t/nsmc
# x, y 데이터를 반환하는 함수를 만드세요
# 김윤 박사 cnn sentence 검색하면 깃헙 나옴
# 해당 사이트에서 clean_str 함수를 찾아서 우리 코드에 적용하세요
# 모든 문서의 토큰 갯수를 그래프로 그려보세요
def clean_str(string, TREC=False):
"""
Tokenization/string cleaning for all datasets except for SST.
Every dataset is lower cased except for TREC
"""
string = re.sub(r"[^가-힣A-Za-z0-9(),!?\'\`]", " ", string)
string = re.sub(r"\'s", " \'s", string)
string = re.sub(r"\'ve", " \'ve", string)
string = re.sub(r"n\'t", " n\'t", string)
string = re.sub(r"\'re", " \'re", string)
string = re.sub(r"\'d", " \'d", string)
string = re.sub(r"\'ll", " \'ll", string)
string = re.sub(r",", " , ", string)
string = re.sub(r"!", " ! ", string)
string = re.sub(r"\(", " \( ", string)
string = re.sub(r"\)", " \) ", string)
string = re.sub(r"\?", " \? ", string)
string = re.sub(r"\s{2,}", " ", string)
return string.strip() if TREC else string.strip().lower()
def get_data(file_path):
# 8544678 뭐야 이 평점들은.... 나쁘진 않지만 10점 짜리는 더더욱 아니잖 0
txt = open('data/ratings_' + file_path + '.txt', 'r', encoding='utf-8')
txt.readline()
# for t in text:
# print(t.strip().split('\t')) # strip -> 개행문자 없앰, '\t' -> tab 없앰
x, y = [], []
for _, doc, label in csv.reader(txt, delimiter='\t'): # 개행문자 기준으로 알아서 한줄 씩
x.append(clean_str(doc).split())
y.append(label)
txt.close()
# print(*x[:3], sep='\n')
# return x, y # 이대로 하면 메모리 터짐
return x[:1000], y[:1000]
x_train, y_train = get_data('train')
x_test, y_test = get_data('test')
# train 데이터로 학습하고 test 데이터에 대해 정확도를 구하세요
# 1. 먼저 voc -> train data
def make_vocab(documents, vocab_size=2000): # 사실 2천개는 너무 적음 만개는 해야함
# words = nltk.corpus.movie_reviews.words()
all_words = collections.Counter([w for doc in documents for w in doc])
most_2000 = all_words.most_common(vocab_size) # 최빈 값을 찾아줌
return [w for w, _ in most_2000] # 최빈 값은 사용하지 않을 것임
# 2. make feature 해주기
def make_feature(doc_words, vocab): # filename = 리뷰룰 앍어오는 파일 이름
# doc_words = nltk.corpus.movie_reviews.words(filename)
feature, uniques = {}, set(doc_words) # uniques <- 중복 x 검색 빠르게 할려고
for v in vocab:
feature['has_{}'.format(v)] = (v in uniques) # uniques 안의 v를 찾아 true false 넣어줌
# feature 수 2천개
return feature
# 3. data 만들기
def make_feature_data(documents, lables, vocab):
# return [(make_feature(name), lables) for name, gender in documents] # 제일 어려운 부분
# return [(make_feature(documents[i], vocab), lables[i]) for i in range(len(lables))]
return [(make_feature(doc, vocab), label) for doc, label in zip(documents, lables)]
def show_freq_dist(documents):
# freq = collections.Counter([t for token in documents for t in token])
heights = sorted([len(doc) for doc in documents])
# print(freq)
plt.plot(range(len(heights)), heights)
plt.show()
# 모든 문서의 토큰 길이를 25개로 맞춰 주세요
# 긴 것은 삭제 부족한 부분은 공백 토큰으로 채웁니다
def make_same_length(documents, max_len):
new_docs = []
for doc in documents:
doc_len = len(doc)
if doc_len < max_len:
new_docs.append(doc + [''] * (max_len - doc_len))
else:
new_docs.append(doc[:max_len])
assert (len(new_docs[-1]) == max_len) # bool 값만 전달 가능 False -> 비정상 종료
return new_docs
# print(x_train)
# show_freq_dist(x_train) # 토큰 40개 정도면 대부분의 리뷰를 포함
# exit(-1)
vocab = make_vocab(x_train, vocab_size=2000)
x_train = make_same_length(x_train, 25)
x_test = make_same_length(x_test, 25)
#
# # 올바른 make_feature_data
train_set = make_feature_data(x_train, y_train, vocab)
test_set = make_feature_data(x_test, y_test, vocab)
clf = nltk.NaiveBayesClassifier.train(train_set) # 엄청 빠름 왜? 정확도가 떨어지니깐
print('acc :', nltk.classify.accuracy(clf, test_set)) # 결과 정답빈도를 알려줌
'인공지능 > RNN' 카테고리의 다른 글
Callback ( check_point와 Earlystopping) (0) | 2020.12.15 |
---|---|
pop corn DBset으로 Baseline, rnn, cnn, cnn-tf, word2vec, nltk 구성하기 (0) | 2020.12.15 |
자연어 처리 ( text에 있는 word에 대한 빈도수 도출하기 ) (0) | 2020.11.24 |
자연어 처리 (Gensim) (0) | 2020.11.24 |
자연어처리( doc2vec ) (0) | 2020.11.22 |