「Twitterデータを使って、何か面白いことができないか」の第三弾です。
第一回:
「停電」に関するツイートをpythonで収集して、WordCloudで可視化してみた
https://qiita.com/pocket_kyoto/items/0f43c9fdce87bddd31cf
第二回:
「クッパ姫」に関するツイートをpythonで収集して、バースト検出してみた
https://qiita.com/pocket_kyoto/items/de4b512b8212e53bbba3
今回は、シンプルに、指定アカウントのツイートを取得して、
WordCloudで可視化してみました。
Twitterデータって、どうやったら収集できるの?
以下の流れで収集できます。
- 開発者用のTwitterアカウントを登録する
- Twitter APIに利用者登録する
- API利用のためのアクセスキー・トークンを取得
- Twitter REST APIsで、データを収集
詳しくは、第一回記事を御覧ください。
指定アカウントのツイートを収集する
まずは、ライブラリの読み込みなど、ツイート収集の準備です。
Twitter REST APIsの出力は、json形式であるため、jsonライブラリを使います。
また、pythonからREST APIsを簡単に呼び出せるように、requests_oauthlibライブラリを使います。
# Twitterデータ収集用のログインキーの情報
KEYS = { # 自分のアカウントで入手したキーを記載
'consumer_key':'*********************',
'consumer_secret':'*********************',
'access_token':'*********************',
'access_secret':'*********************',
}
# Twitterデータの収集(収集準備)
import json
from requests_oauthlib import OAuth1Session
twitter = OAuth1Session(KEYS['consumer_key'],KEYS['consumer_secret'],KEYS['access_token'],KEYS['access_secret'])
指定アカウントのツイート収集用の関数は、以下のように書きました。
user_name(@以降のアカウント名)を引数としています。
1回あたり最大100ツイートしか検索できないため、for文で複数回リクエストできるようにしています。
# Twitterデータ取得関数
def getAccountTwitterData(user_name, repeat=10):
url = "https://api.twitter.com/1.1/statuses/user_timeline.json"
params ={'screen_name':user_name,'exclude_replies':True,'include_rts':False,'count':200} #取得パラメータ
tweets = []
mid = -1
for i in range(repeat):
if mid != -1: # 初回のみmax_idの指定を解除する
params['max_id'] = mid # midよりも古いIDのツイートのみを取得する
res = twitter.get(url, params = params)
if res.status_code == 200: #正常通信出来た場合
sub_tweets = json.loads(res.text) #レスポンスからツイート情報を取得
user_ids = []
for tweet in sub_tweets:
user_ids.append(int(tweet['id']))
tweets.append(tweet)
# ループで取得したmidよりも古いツイートを取るための工夫(※もっと良い書き方ありそう)
if len(user_ids) > 0:
min_user_id = min(user_ids)
mid = min_user_id - 1
else:
mid = -1
print(mid) # 時系列で見た時に最も古いツイートID
else: #正常通信出来なかった場合
print("Failed: %d" % res.status_code)
break
print("ツイート取得数:%s" % len(tweets))
return tweets
この関数を用いて、特定ユーザーのツイートを収集してみます。
総フォロワー数ランキング1位の有吉弘行さんのアカウント("ariyoshihiroiki")のツイートを収集してみます。
tweets = getAccountTwitterData("ariyoshihiroiki", repeat=30)
出力:
1083030050134323201
1052193588430364671
1022730204936953855
996980908119900161
965901986422927360
927507559023460352
901354707137871872
883995701314584575
850964015756869631
823160757894291455
796014648101175296
781414278850936831
763211195511771135
747450926097563647
728578679194820607
708969135716196351
706835898747367423
-1
:
(中略)
:
-1
ツイート取得数:2520
2520のツイートを収集できました。
一定量のツイートは収集できましたが、Twitter APIから、特定ユーザーの全ツイートにアクセスすることは仕様上できないようです。
取得したツイートを可視化する
以下のような関数を定義して、janomeで形態素解析して、単語の出現頻度をカウントした後、WordCloudで可視化しました。
# 文章を形態素解析して、Bag of Wordsに変換する
from janome.tokenizer import Tokenizer
import collections
import re
def CountWord(tweets):
tweet_list = [tweet["text"] for tweet in tweets]
all_tweet = "\n".join(tweet_list)
t = Tokenizer()
# 原形に変形、名詞のみ、1文字を除去、漢字・平仮名・カタカナの連続飲みに限定
c = collections.Counter(token.base_form for token in t.tokenize(all_tweet)
if token.part_of_speech.startswith('名詞') and len(token.base_form) > 1
and token.base_form.isalpha() and not re.match('^[a-zA-Z]+$', token.base_form))
freq_dict = {}
mc = c.most_common()
for elem in mc:
freq_dict[elem[0]] = elem[1]
return freq_dict
WordCloudで可視化する関数
# Word Cloudで可視化、WordCloud可視化関数
def color_func(word, font_size, position, orientation, random_state, font_path):
return 'white'
from wordcloud import WordCloud
import matplotlib.pyplot as plt
get_ipython().run_line_magic('matplotlib', 'inline')
from matplotlib.font_manager import FontProperties
fp = FontProperties(fname=r'C:\WINDOWS\Fonts\meiryo.ttc', size=50) #日本語対応
def DrawWordCloud(word_freq_dict, fig_title):
# デフォルト設定を変更して、colormapを"rainbow"に変更
wordcloud = WordCloud(background_color='white', min_font_size=15, font_path='C:\WINDOWS\Fonts\meiryo.ttc',
max_font_size=200, width=1000, height=500, prefer_horizontal=1.0, relative_scaling=0.0, colormap="rainbow")
wordcloud.generate_from_frequencies(word_freq_dict)
plt.figure(figsize=[20,20])
plt.title(fig_title, fontproperties=fp)
plt.imshow(wordcloud,interpolation='bilinear')
plt.axis("off")
有吉弘行さんのアカウントに含まれるツイートを可視化してみます。
freq_dict = CountWord(tweets)
DrawWordCloud(freq_dict, "%sさんのつぶやきキーワード" % "ariyoshihiroiki")
できました。
ラジオという単語や、田中さん、上島さんなどの仲の良いメンバーの名前が目立ちます。
ちなみに孫正義さんのアカウント("masason")のツイートを可視化すると以下のようになります。
tweets = getAccountTwitterData("masason", repeat=30)
freq_dict = CountWord(tweets)
DrawWordCloud(freq_dict, "%sさんのつぶやきキーワード" % "masason")
出力:
329646069589884927
241826873217257472
:
(中略)
:
-1
ツイート取得数:3068
原発関連のツイートが目立つことが分かります。
まとめと今後
高度な分析に取り組もうとすると、やはりREST APIs で収集できる範囲では不足な気がしますが、
ユーザーアカウント毎のツイートを簡易に取得できることが分かったので、応用できそうな予感はします。
Twitterデータの他の活用方法についても探っていこうと思います。