아마추어 언어 처리 100 개 노크 : 39
12168 단어 mecab형태소 분석파이썬언어 처리 100개 노크자연 언어 처리
제4장: 형태소 해석
나츠메 소세키의 소설 「고배는 고양이이다」의 문장(neko.txt)을 MeCab를 사용해 형태소 해석해, 그 결과를 neko.txt.mecab라는 파일에 보존하라. 이 파일을 사용하여 다음 질문에 해당하는 프로그램을 구현하십시오.
문제 37, 38, 39는 matplotlib 또는 Gnuplot을 사용할 수 있습니다.
39. Zipf의 법칙
단어의 출현 빈도 순위를 가로축, 그 출현 빈도를 세로축으로, 양 대수 그래프를 플롯하라.
완성된 코드:
main.py
# coding: utf-8
import MeCab
from collections import Counter
import matplotlib.pyplot as plt
from matplotlib.font_manager import FontProperties
fname = 'neko.txt'
fname_parsed = 'neko.txt.mecab'
def parse_neko():
'''「吾輩は猫である」を形態素解析
「吾輩は猫である」(neko.txt)を形態素解析してneko.txt.mecabに保存する
'''
with open(fname) as data_file, \
open(fname_parsed, mode='w') as out_file:
mecab = MeCab.Tagger()
out_file.write(mecab.parse(data_file.read()))
def neco_lines():
'''「吾輩は猫である」の形態素解析結果のジェネレータ
「吾輩は猫である」の形態素解析結果を順次読み込んで、各形態素を
・表層形(surface)
・基本形(base)
・品詞(pos)
・品詞細分類1(pos1)
の4つをキーとする辞書に格納し、1文ずつ、この辞書のリストとして返す
戻り値:
1文の各形態素を辞書化したリスト
'''
with open(fname_parsed) as file_parsed:
morphemes = []
for line in file_parsed:
# 表層形はtab区切り、それ以外は','区切りでバラす
cols = line.split('\t')
if(len(cols) < 2):
raise StopIteration # 区切りがなければ終了
res_cols = cols[1].split(',')
# 辞書作成、リストに追加
morpheme = {
'surface': cols[0],
'base': res_cols[6],
'pos': res_cols[0],
'pos1': res_cols[1]
}
morphemes.append(morpheme)
# 品詞細分類1が'句点'なら文の終わりと判定
if res_cols[1] == '句点':
yield morphemes
morphemes = []
# 形態素解析
parse_neko()
# Counterオブジェクトに単語をセット
word_counter = Counter()
for line in neco_lines():
word_counter.update([morpheme['surface'] for morpheme in line])
# 全件取得
list_word = word_counter.most_common()
# 出現数のリスト取得
counts = list(zip(*list_word))[1]
# グラフで使うフォント情報(デフォルトのままでは日本語が表示できない)
fp = FontProperties(
fname='/usr/share/fonts/truetype/takao-gothic/TakaoGothic.ttf'
)
# 散布図のデータ指定
plt.scatter(
range(1, len(counts) + 1), # x軸:順位
counts # y軸:出現頻度
)
# 軸の値の範囲の調整
plt.xlim(1, len(counts) + 1)
plt.ylim(1, counts[0])
# 対数グラフに
plt.xscale('log')
plt.yscale('log')
# グラフのタイトル、ラベル指定
plt.title("39. Zipfの法則", fontproperties=fp)
plt.xlabel('出現度順位', fontproperties=fp)
plt.ylabel('出現頻度', fontproperties=fp)
# グリッドを表示
plt.grid(axis='both')
# 表示
plt.show()
실행 결과:
산점도
parse_neko()
와 neco_lines()
는 전문 과 같습니다.이번에는 산포도로 해 보았습니다. 산점도는 pyplot.scatter() 에 x축의 배열과 y축의 배열을 건네주면 만들어 줍니다. 간단!
로그 그래프로 만들려면 pyplot.xscale() 과 pyplot.yscale() 로 지정합니다.
Zipf의 법칙이란?
지퍼라든지 지프라든지 읽을 것 같고, 무언가를 집계했을 때, 그 출현 빈도가 높은 순서로 늘어놓으면
(個々の順位)×(その出現頻度)
가 일정해지는 법칙이라고 합니다. 이 법칙대로의 경우는 양 대수 그래프에 쓰면 비스듬히 내려가는 직선이 됩니다. 확실 해지고 있습니다.단어의 출현 빈도뿐만 아니라 여러가지 자연 현상, 사회 현상으로 이루어지는 경우가 있는 것 같습니다. 왠지 이상하다. 관심있는 분은 구구 해보세요.
40번째 노크는 이상입니다. 실수 등이 있으시면 지적해 주시면 감사하겠습니다.
실행 결과에는 100개 노크에서 사용하는 코퍼스 데이터 로 배포된 데이터의 일부가 포함됩니다. 이 4장에서 사용하고 있는 데이터는 푸른 하늘 문고 로 공개되고 있는 나츠메 소세키의 장편 소설 '고배는 고양이이다'가 바탕으로 되어 있습니다.
Reference
이 문제에 관하여(아마추어 언어 처리 100 개 노크 : 39), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://qiita.com/segavvy/items/e0a7994cc63c8be7380b텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)