皆さま、こんにちは、ソニー・ミュージックマーケティングユナイテッドのたまごです。
普段は、アーティストのデジタルマーケティングを行う部門で、アドホックなデータ分析や市場リサーチなどを担当しています。
我々のチームでは、分析用途に応じて、SNSや音楽配信サービスなど、さまざまなサービスからデータ収集を行っています。
前回は、YouTube Analytics APIを利用して、アーティストのYouTubeチャンネルの情報(動画再生数や視聴者の属性)を取得する方法を紹介しました。 今回は、収集した情報をどのように分析するかの一例として、性別・年代に基づいた動画のマッピングについてお話しします。
よくある悩み
「これまでアーティストのYouTubeチャンネルからいろんな動画を上げてきたけど、どの動画がどんな層によく見られているのか分からないなあ。過去のデータを見て、何か今後のヒントになるような情報を見つけられないだろうか」
こんな相談が、レーベルのA&R(アーティスト&レパートリー)から寄せられたとします。
前回の記事によれば、Data APIとAnalytics APIを組み合わせれば、自分のチャンネル内の動画の性別・年代といった情報が一括で取得できるのでした。
APIをうまく利用して、以下のようなデータが得られたとしましょう。 (今回は、実際にAPIで取得したアーティストチャンネルのデータを、扱いやすい形に加工したものをサンプルとして見ていきます。動画名などは仮で入れている点にご注意ください。)
さて、各動画の性別・年代ごと視聴数の傾向を探るために、このデータをどのように可視化してあげると良いでしょう。
棒グラフで比較すれば、情報を落とすことなく比較ができそうです。 ただ、性別と年代の組み合わせを出すのは変数が多くなりすぎて難しそうですし、どの数字を見ればいいか目移りしてしまいます。
2カテゴリの組み合わせを出すなら、ヒートマップも良いかもしれません。しかし、動画の数だけ表を並べてそれぞれの関係を調べるのは大変そうです。
つまるところ、性別・年代ごとの再生数といった、多変量データを分析するにあたり、情報を全く落とすことなく可視化するのは難しいことが分かります。
今回は、可視化の1つのアプローチとして、コレスポンデンス分析を用いた2次元マッピングを試してみようと思います。
コレスポンデンス分析とは
多変量解析において、データの情報を極力落とすことなく、少ない変数でその特徴を説明しようとする、「次元削減」のアプローチの1つです。マーケティングの分野では、アンケートの回答結果を2次元にマッピングするような目的でよく用いられるようです。
ちなみに、次元削減の方法としてよく知られる似た手法に「主成分分析」がありますが、主成分分析は量的データ、コレスポンデンス分析は質的データを扱うという風に使い分けます。
今回は、コレスポンデンス分析を用いて、各動画の性別×年代ごとの再生数のクロス集計表のデータを、2次元散布図にマッピングすることを考えます。
実際の計算はやや込み入った話になるので今回は省略しますが、いつか理論面にフォーカスした記事も当ブログで紹介できればと思っています。
デモンストレーション
前回同様、Jupyter Notebookなど、インタラクティブにPythonを実行する環境を想定しています。
冒頭お見せした通り、pandas DataFrameの形で、各動画タイトルの性別・年代ごとの再生数がテーブル形式で得られているものとします。 dfという変数にDataFrameが代入されている前提のため、以下のコード単体では動きません。
まず、このデータをクロス集計表の形に直しておきます。 各動画タイトルをサンプル(行)、性別・年代の組み合わせを変数(列)として、pandasのpivot_table関数を用います。
# 変数dfにFig.1のようなデータフレームが入っている想定。これをクロス集計表の形に変換 df_cross = pd.pivot_table( df, columns=['ageGroup', 'gender'], index='title', values='views', aggfunc='sum').fillna(0)
Pythonでは、mcaライブラリを用いて、pandasのクロス集計表に対して簡単にコレスポンデンス分析を実行できます。
必要に応じてインストールを行ってください。
python3 -m pip install --user mca
それでは、mcaライブラリでコレスポンデンス分析を実行してみましょう。
今回は、PyPI上のUsage notesやノートブックを参考に進めています。
# ライブラリのインポート import mca # 分析の実行 mca_ind = mca.MCA( df_cross, # df_crossに対して実行 benzecri=False # 主軸の寄与度の過小評価を補正するか否かのフラグ。ここでは説明省略します ) # 行(動画タイトル)、列(性別・年代)のfactor scores(マッピング先の平面における各点の座標)の取得 rows = mca_ind.fs_r(N=2) cols = mca_ind.fs_c(N=2)
行、列それぞれの2次元座標が得られたので、実際にプロットしてみましょう。
ここで、ブログ内で直接動画タイトルを出せない都合、以下ソースコードでは「行ラベルの付与」を行っていませんが、必要に応じて「列ラベルの付与」と同様に進めると良いでしょう。 一方で、サンプル数が多い場合、ラベルを付与すると煩雑になる場合もあるので、例えばplotlyなどでインタラクティブなグラフ作成を試みるのも良いかもしれません。
import matplotlib.pyplot as plt from adjustText import adjust_text fig, ax = plt.subplots(figsize=(7,7)) # 行(動画タイトル)のプロット ax.scatter(row_fs[:, 0], row_fs[:, 1], s=120, marker='o', c='skyblue', alpha=.5) # 列(性別・年代)のプロット ax.scatter(col_fs[:, 0], col_fs[:, 1], s=120, marker='x', c='red', alpha=.5) # 列ラベルの付与 labels = df_cross.columns.values texts = [] for label,x,y in zip(labels, col_fs[:,0], col_fs[:,1]): texts.append(ax.annotate(label,xy = (x, y), fontsize=8)) # 見づらいのが嫌なのでadjust_text。本質的には不要 adjust_text(texts, arrowprops=dict(arrowstyle='->', color='gray')) # 原点に線を引く ax.axhline(0, color='gray') ax.axvline(0, color='gray') plt.title('アーティストチャンネルのYouTube動画の性年代別再生数のコレスポンデンス分析') plt.xlabel('Factor 1') plt.ylabel('Factor 2') plt.show()
実行すると、以下左図のような散布図が得られます。
ここで、赤のX印が性別・年代の組み合わせを、青の●印が各動画タイトルを表します。 グラフ内で要素間の距離が近いほど、それぞれの関係が強いことを意味します。
ご参考までに、実際のデータから得られた簡単な考察を右方に載せています。どのような動画がどの層から人気が高いのか大まかな特徴が分かったため、ここから再生経路の違いを見たり、さらに細かくデータを調べていくことで、A&Rの要望に応えてあげることができそうです。
コレスポンデンス分析を用いることで、棒グラフやヒートマップ対比で情報は少なくなるものの、見通し良く全体の傾向を掴むことができました。
なお、コレスポンデンス分析においては、2変数まででどこまで元の情報が説明できているかなど、他にもチェックすべき項目がありますが、今回は省略します。 いずれ理論に関する記事を書く際に改めてご紹介できればと思います。
最後に
YouTubeのAPIで収集した、性別・年代ごとの動画再生数を、コレスポンデンス分析を用いて可視化してみました。
当然ですが、今回ご紹介した可視化の方法が、分析において必ずしも最良というわけではありません。 動画をドメイン知識に基づいてジャンル分けしたり、機械学習等でクラスタ分けして、それぞれの違いを比較することもできるかもしれません。また、そもそも2次元までの軸ではどうしてもデータの特徴を説明できない、コレスポンデンス分析を用いるのが不適切なケースもあるでしょう。 分析の目的や、データの中身に応じて、適切なアプローチを考慮することが必要です。また、資料化に当たっては、グラフの見栄えの調整や、情報の取捨選択も別途検討すべきでしょう。
とはいえ、コレスポンデンス分析はクロス表の可視化として強力な手法の1つです。 使えるかも! というタイミングがあれば、ぜひ一度試してみてください。