形態素解析では、文章の特徴を分析するために、単語の品詞を求めます。
ここでは、BoWの対象を名詞と動詞に限定します。
対象を絞ることで、特徴が使いやすくなります。
データは、下記の2冊の小説の文章の抜粋が入ったdata.csvを使います。
坊っちゃん:夏目漱石 著
銀河鉄道の夜:宮沢賢治 著
import pandas as pd
from collections import Counter
from janome.tokenizer import Tokenizer
df = pd.read_csv('input/data.csv', encoding='utf-8')
df[:3]
def calc_bow(text, tokenizer):
tokens = tokenizer.tokenize(text)
tokens = [token.base_form for token in tokens
if token.part_of_speech.startswith(('名詞', '動詞'))]
return Counter(tokens)
- 品詞は、
token.part_of_speech
に「品詞、品詞細分類1、品詞細分類2、品詞細分類3」の形式で入っています。 - 「名詞または動詞かどうか」は、
token.part_of_speech.startswith(('名詞', '動詞'))
で確認できます。startswith(('名詞', '動詞'))
とすると、書き出しが「名詞」か「動詞」のどちらかで始まることを判断できます。
tokenizer = Tokenizer()
bow = calc_bow(df.Content[0], tokenizer)
print(bow)
Counter({'する': 3, '二': 3, '階': 3, '飛び降りる': 3, '抜かす': 3, 'ある': 3, '時': 2, 'いる': 2, '一': 2, '腰': 2, '事': 2, '人': 2, '親譲り': 1, '無鉄砲': 1, '供': 1, '損': 1, '小学校': 1, '居る': 1, '時分': 1, '学校': 1, '週間': 1, '無闇': 1, '聞く': 1, '知れる': 1, '理由': 1, '新築': 1, '首': 1, '出す': 1, '同級生': 1, '冗談': 1, '威張る': 1, 'そこ': 1, '出来る': 1, '弱虫': 1, 'ー': 1, 'い': 1, '囃す': 1, '小使': 1, '負ぶさる': 1, '帰る': 1, '来る': 1, 'おやじ': 1, '眼': 1, '奴': 1, '云う': 1, '次': 1, '飛ぶ': 1, '見せる': 1, '答える': 1})
全行についてBoWを計算し、変数bowsに入れましょう。
bows = df.Content.apply(calc_bow, tokenizer=tokenizer)
print(bows)
0 {'親譲り': 1, '無鉄砲': 1, '供': 1, '時': 2, '損': 1, '... 1 {'親類': 1, 'もの': 1, '西洋': 1, '製': 1, 'ナイフ': 2, ... 2 {'庭': 2, '東': 1, '二': 1, '十': 2, '歩': 1, '行く':... 3 {'鉢': 1, '開く': 1, '頭': 3, 'こっち': 1, '胸': 1, '宛... 4 {'外': 1, 'いたずら': 1, 'やる': 1, '大工': 1, '兼': 1, ... 5 {'おやじ': 2, 'おれ': 2, '可愛がる': 1, 'くれる': 1, '母': ... 6 {'母': 2, '病気': 1, '死ぬ': 4, '二': 1, '三': 1, '日'... 7 {'母': 1, '死ぬ': 1, 'おやじ': 5, '兄': 3, '三': 1, '人... 8 {'時': 1, '仕方': 1, '観念': 1, 'する': 6, '先方': 1, '... 9 {'おれ': 5, '人': 2, '好く': 1, 'れる': 2, '性': 1, 'あ... 10 {'母': 1, '死ぬ': 1, '清': 2, 'おれ': 2, 'がる': 1, '供... 11 {'三': 3, '円': 4, '蝦蟇口': 2, '入れる': 2, '懐': 1, '... 12 {'みなさん': 1, 'ふう': 1, '川': 1, '言う': 2, 'れる': 2,... 13 {'ジョバンニ': 5, 'さん': 2, 'あなた': 1, 'わかる': 1, 'いる'... 14 {'先生': 1, '意外': 1, 'よう': 1, 'カムパネルラ': 1, '見る':... 15 {'ジョバンニ': 2, '赤': 1, 'なる': 3, 'うなずく': 1, 'いつか'... 16 {'天の川': 5, 'ほんとう': 1, '川': 3, '考える': 2, '一つ': ... 17 {'先生': 1, '中': 3, 'たくさん': 2, '光る': 5, '砂': 1, ... 18 {'教室': 2, 'じゅう': 1, '机': 1, '蓋': 1, 'あける': 1, ... Name: Content, dtype: object
apply
を使うことで、全行について、BoWをまとめて計算できます。
bows = pd.Series([calc_bow(c, tokenizer=tokenizer)
for c in df.Content], name='Content')
このプログラムとやっていることは同じ
コメント