メインコンテンツまでスキップ

txtファイルから文を拾ってMeCabで形態素解析をしてWordCloudを出力する(Python)

· 約4分
Hanamaru
Openchat Owner

任意のテキストファイルに以下のような文が書き込まれているとする。

ねむ
なんだこれは!
きつ
つら

寝たか
寝てないよ
起きた
だる
おはよう
なんかオプチャで滑るの恥ずかしいよね
皆さんこんにちは
こんにちは
ひーちゃんスプラ買わないの?
😅
………
どうしよ。。。

このとき、このテキストファイルの文を基にワードクラウドを作成するコードを示す。

from wordcloud import WordCloud
import MeCab
import os

# テキストファイルのパス
text_file_path = "***テキストファイルのパスを指定***"
# 保存先のフォルダパス
folder_path = "***画像出力先を指定***"
# 参照するフォントのフォルダパス
font_path = "***.ttfを指定***"

# テキストファイルからテキストを読み込む
with open(text_file_path, 'r', encoding='utf-8') as file:
text = file.read()

# MeCabの初期化
mecab = MeCab.Tagger("C:\Program Files\MeCab\dic\ipadic")

# 形態素解析
node = mecab.parseToNode(text)
output = []
#意味をなさないような単語を除外する。
stoplist = ['あ', 'い', 'う', 'え', 'お', 'か', 'き', 'く', 'け', 'こ', 'さ', 'し', 'す', 'せ', 'そ',
'た', 'ち', 'つ', 'て', 'と', 'な', 'に', 'ぬ', 'ね', 'の', 'は', 'ひ', 'ふ', 'へ', 'ほ',
'ま', 'み', 'む', 'め', 'も', 'や', 'ゆ', 'よ', 'ら', 'り', 'る', 'れ', 'ろ', 'わ', 'を', 'ん',
'ア', 'イ', 'ウ', 'エ', 'オ', 'カ', 'キ', 'ク', 'ケ', 'コ', 'サ', 'シ', 'ス', 'セ', 'ソ',
'タ', 'チ', 'ツ', 'テ', 'ト', 'ナ', 'ニ', 'ヌ', 'ネ', 'ノ', 'ハ', 'ヒ', 'フ', 'ヘ', 'ホ',
'マ', 'ミ', 'ム', 'メ', 'モ', 'ヤ', 'ユ', 'ヨ', 'ラ', 'リ', 'ル', 'レ', 'ロ', 'ワ', 'ヲ', 'ン',
'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T',
'U', 'V', 'W', 'X', 'Y', 'Z',
'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z',
'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z',
'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z',
'ある', 'ない', 'する', 'いい', 'きっ', 'なっ', 'なさい', 'もん', 'ため', 'おり', 'あり', 'いっ']

while node:
word_type = node.feature.split(",")[0]
if word_type in ["名詞","形容詞","動詞"]:
if not node.surface in stoplist and not node.surface.isdigit():
output.append(node.surface.upper())
node = node.next

#print(output)
#print(len(output))

#形態素解析された単語のリストをWordCloud用に処理
text = ' '.join(output)

print(text)

# ワードクラウドの生成
# collocationsをFalseにしないと重複して現れる単語がある
# 色はbackground_color=(255, 202, 191)でも指定可能(RGB)
wordcloud = WordCloud(background_color='white', font_path=font_path, collocations = False, width=1920,height=1080).generate(text)

# フォルダが存在しない場合は作成する
if not os.path.exists(folder_path):
os.makedirs(folder_path)

# WordCloudを画像として保存
wordcloud_file_path = os.path.join(folder_path, "wordcloud.png")
wordcloud.to_file(wordcloud_file_path)

# 保存したパスを表示
print("ワードクラウドが保存されました:", wordcloud_file_path)

なお、あらかじめ以下のページから MeCab をインストールし、辞書をコード内で明示する必要がある。

(# MeCab の初期化 の部分)

https://github.com/ikegami-yukino/mecab/releases

完成品は「月別オプチャトレンド」を見てほしい。

上記に掲載した図はこれらの他、色々調整してある。

特定のチャンネルのチャットを時期を指定してCSVで取得する(Python)

· 約2分
Hanamaru
Openchat Owner

CSV と TXT で保存している。API なので、あまりループさせると相手のサーバに迷惑がかかるので留意。

パスを指定しないと、Windows ならユーザー直下に保存される(はず)

import requests
import csv
from datetime import datetime, timedelta, date

'''
M_ID はhttps://www.openrec.tv/live/gkrpkm6ljz5 の gkrpkm6ljz5 が該当
start_at はチャット取得の起点とする日時
filename にはファイルパス等を指定
today は実行時の日時がセットされる → 終点の時間指定をしたい場合は書き換え
'''

M_ID = 'gkrpkm6ljz5'
start_at = '2024-01-01T15:00:00'
filename = "chat_data.csv"
today = date.today().isoformat()

# API を叩く
endpoint = f"https://public.openrec.tv/external/api/v5/movies/{M_ID}/chats"
limit = 300

params = {
"from_created_at": start_at,
"is_including_system_message": "false",
"limit": str(limit)
}

headers = ["Posted At", "Nickname", "User ID", "Message", "Recxuser ID"]

# ループ回数のカウンターを初期化
loop_count = 0

with open(filename, "w", newline="", encoding="utf-8") as file:
writer = csv.writer(file)
writer.writerow(headers)

while True:
response = requests.get(endpoint, params=params)
data = response.json()

if not data:
break

# ループ回数のカウンターをインクリメント
loop_count += 1

for item in data:
nickname = item["user"]["nickname"]
user_id = item["user"]["id"]
message = item["message"]
posted_at = item["posted_at"]
recxuser_id = item["user"]["recxuser_id"]

posted_at_datetime = datetime.fromisoformat(posted_at)
formatted_posted_at = posted_at_datetime.strftime("%Y/%m/%d %H:%M:%S")

row = [formatted_posted_at, nickname, user_id, message, recxuser_id]
writer.writerow(row)

last_posted_at = data[-1]["posted_at"]
next_posted_at_datetime = datetime.fromisoformat(last_posted_at) + timedelta(seconds=1)
next_posted_at_str = next_posted_at_datetime.strftime("%Y-%m-%dT%H:%M:%S")

if next_posted_at_str[:10] >= today:
break

params["from_created_at"] = next_posted_at_str
print(next_posted_at_str)

# ループ回数(累計)を表示
print("Total loop count:", loop_count)