はじめに
ウェブサービスのユーザがどのページからどのページに移っていっているのかとか、どの工程からどの工程に仕掛品が流れていったのかなどをPythonで可視化したい。
ここでは仮に以下のようなどのページからどのページに移っていったのかについて集計したデータがあったとする。
|
from |
to |
count |
0 |
A |
A |
111 |
1 |
A |
B |
1120 |
2 |
A |
C |
1230 |
3 |
B |
A |
214 |
4 |
B |
B |
1225 |
5 |
B |
C |
1216 |
6 |
C |
A |
327 |
7 |
C |
C |
2319 |
こんな感じでページ→ページの遷移数と遷移確率行列的なものを可視化したい。
![c_matrix.png](https://qiita-user-contents.imgix.net/https%3A%2F%2Fqiita-image-store.s3.ap-northeast-1.amazonaws.com%2F0%2F213259%2Ffd1812d5-0290-d7e5-2300-ce90e61d2027.png?ixlib=rb-4.0.0&auto=format&gif-q=60&q=75&s=64ced3ab8c76028e341110acf740dd6c)
![p_matrix.png](https://qiita-user-contents.imgix.net/https%3A%2F%2Fqiita-image-store.s3.ap-northeast-1.amazonaws.com%2F0%2F213259%2F6399151d-f838-19de-0c5e-9c531c8abdd6.png?ixlib=rb-4.0.0&auto=format&gif-q=60&q=75&s=4fee2d35c725508924c2dbd4431721b8)
実装
以下でpandas, seaborn, matplotlibを使ってJupyter上で可視化する。
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
df = pd.DataFrame({'from': ['A', 'A', 'A', 'B', 'B', 'B', 'C', 'C'],
'to': ['A', 'B', 'C', 'A', 'B', 'C', 'A', 'C'],
'count': [111, 1120, 1230, 214, 1225, 1216, 327, 2319]})
df # C→Bのページ遷移は0件とする
|
from |
to |
count |
0 |
A |
A |
111 |
1 |
A |
B |
1120 |
2 |
A |
C |
1230 |
3 |
B |
A |
214 |
4 |
B |
B |
1225 |
5 |
B |
C |
1216 |
6 |
C |
A |
327 |
7 |
C |
C |
2319 |
pages = sorted(list(set(df['from'].values) | set(df['to'].values)))
pages
count_matrix = pd.DataFrame(index=pages, columns=pages, dtype=float)
count_matrix
|
A |
B |
C |
A |
NaN |
NaN |
NaN |
B |
NaN |
NaN |
NaN |
C |
NaN |
NaN |
NaN |
for i in zip(df['from'].values, df['to'].values, df['count'].values):
count_matrix.at[i[0], i[1]] = i[2]
count_matrix.fillna(0, inplace=True)
row_sum = count_matrix.sum(axis=1)
row_sum
A 2461.0
B 2655.0
C 2646.0
dtype: float64
probabilistic_matrix = count_matrix.div(row_sum, axis=0)
probabilistic_matrix
|
A |
B |
C |
A |
0.045104 |
0.455100 |
0.499797 |
B |
0.080603 |
0.461394 |
0.458004 |
C |
0.123583 |
0.000000 |
0.876417 |
sns.heatmap(count_matrix, annot=True, cmap='coolwarm', fmt='g', vmin=0)
![c_matrix.png](https://qiita-user-contents.imgix.net/https%3A%2F%2Fqiita-image-store.s3.ap-northeast-1.amazonaws.com%2F0%2F213259%2F20e40b3d-c0d7-3e90-7599-9334d841f567.png?ixlib=rb-4.0.0&auto=format&gif-q=60&q=75&s=404c6ac0da051a23d84fa51bf2d4185b)
sns.heatmap(probabilistic_matrix, annot=True, cmap='coolwarm', fmt='.3f', vmin=0, vmax=1)
plt.ylabel('from')
plt.xlabel('to')
plt.show()
![p_matrix.png](https://qiita-user-contents.imgix.net/https%3A%2F%2Fqiita-image-store.s3.ap-northeast-1.amazonaws.com%2F0%2F213259%2F17eaf859-e550-2d7e-b225-a9488102103f.png?ixlib=rb-4.0.0&auto=format&gif-q=60&q=75&s=b1e676b60e4542b8013c2686297f6972)