gepuro.net
gepulog

データ分析エンジニアによる備忘録的ブログ

ユーザのアクセス元の街を可視化してみる

当ブログのユーザのアクセス元を可視化しました。

アクセス元のipアドレスからhttps://freegeoip.net/より提供されるAPIを用いて、どの街かを特定しました。

観測期間は適当です。(freegeoipでデータを取得し始めてからで、過去に遡るのは面倒だった)

以下が結果です。パレート図で描きました。

久しぶりにパレート図を見たわけですが、円グラフに比べて見やすいなあと感じます。もっと流行るとイイなあ。

それにしても、mountain viewって何だろうか。

最後にコードです。

cat data/* |
jq -r '
select(.site=="blog.gepuro.net") |
select(.geo.city != null) |
[.cid, .geo.city] |
@csv' |
sort |
uniq |
header -a '"cid","city"' |
q -H -O -d ',' '
select
case city
when "" then "unknown"
else city
end as city
, count(1)  as count
from -
group by city
order by 2 desc
' |
Rio -r -e 'df %>% mutate(crank=1:n())' |
Rio -r -e 'rbind(df[df$crank<10,c("city","count")], data.frame(city="other", count=sum(df[df$crank > 10,]$count)))' |
Rio -e 'library(qcc); library("devtools"); source("https://gist.githubusercontent.com/abikoushi/722ce195fb70df5cc679/raw/fd434a74d86ab3feb415da33b3f8abb4dd03355f/ParetoChart2.r"); city <- df$count; names(city) <- df$city; png("count_city.png"); pareto.chart2(city, unsorted=TRUE); dev.off()'

Rioを使ったら、読みにくくなってしまった。 qコマンドやjqコマンドと違って、改行を許してくれないんだよなあ。。。 (自分で直せって話だな)

シェルスクリプトでアクセスログを用いてページ間の類似度を求める

協調フィルタリングです。

協調フィルタリングに関しては、「協調フィルタリングについてまとめてみた。」が詳しく書かれており参考になります。

データセットは、いつものようにwebビーコンのログです。

使用したコマンド

  • jq
  • q
  • sed
  • awk
  • mcmd
  • http://datascienceatthecommandline.com/
  • など

実際のコマンド

もう少しクールに書けるような気がします。

cat data/* |  # jsonからデータを取り出してcid, urlのデータを得る
jq -c -r 'select(.site=="blog.gepuro.net")| [.cid, .url] | @csv' |
sed -e 's/\?.*"$/"/' |
grep "http://blog.gepuro.net/archives/" |
sed -e 's/http\:\/\/blog\.gepuro\.net\/archives\///' |
header -a '"cid","url"' | # cidごとにurlのビューをカウントして横持ちにする
q -H -O -d ',' "
select cid, url, count(1) as view
from -
group by cid, url
" |
mcross k=cid f=view s=url v=0 |
cat > tmp/cross.csv

cat tmp/cross.csv | # urlごとのコサイン類似度を求める
msim -d c=cosine f=$(head -n1 tmp/cross.csv | cut -c 11-) |
q -H -O -d ',' '
select fld1, fld2, cosine
from -
where fld1 != fld2
order by fld1, cosine desc

' | # urlごとに上位5件を取得する
sed -e 's/,/ /g' |
body rank ref=1 |
sed -e 's/fld1 fld2 cosine/rank fld1 fld2 cosine/' |
sed -e 's/ /,/g' |
q -H -O -d ',' '
select fld1,fld2 from -
where rank <= 5
' |
mtra k=fld1 f=fld2 | # url,類似記事一覧 というデータの持ち方をする
sed -e 's/fld1%0/fld1/' |
csvjson  # パースしやすいようにjson形式にする

結果

ハードディスクの寿命分布を比較 という記事に対しての結果を見てみます。

アクセスログを使った場合(メモリベース, コサイン類似度)

コンテンツベース, BoWでコサイン類似度

となりました。

さいごに

各記事の下に表示出来たら楽しいなあ。

トップページからページングして2ページ目へのアクセスはあるのか

サイトの顔になるトップページですが、過去の記事へと遡ってくれる人は、どれほどいるのでしょうか。

蓄積しているログを集計しました。 集計期間は、2015/9/14から2016/1/18です。

トップページのPV数482のうち、2ページ目への遷移は16でした。 また、遷移した合計数は123でした。

意外にもサイト内を巡回してくれるのですね。

遷移先を上位から

URL PV数
http://blog.gepuro.net/page/2 16
http://blog.gepuro.net/archives/118 9
http://blog.gepuro.net/category/統計/ 8
http://blog.gepuro.net/archives/131 7
http://blog.gepuro.net/archives/129 6
http://blog.gepuro.net/archives/133 6
http://blog.gepuro.net/archives/136 6
http://blog.gepuro.net/archives/134 5
http://blog.gepuro.net/archives/135 5
http://blog.gepuro.net/archives/119 4

となっていました。

集計期間から推測すると、右側にある「最近の投稿一覧」もクリックされているようです。

他の記事へアクセスして貰いやすくするためには、自動ロードも必要なのかもしれないです。 http://www.infinite-scroll.com/infinite-scroll-jquery-plugin/ こういうのも使ってみたいなあ。

集計用のコマンド

cat data/* |
jq -r '
select(.url == "http://blog.gepuro.net/") |
[.sid, .date, .url] | @csv' |
q -H -O -d ',' '
select
count(1) as pv_toppage
from -
'

echo

cat data/* |
jq -r '
select(.site=="blog.gepuro.net") |
select(.referrer == "http://blog.gepuro.net/") |
select(.url != "http://blog.gepuro.net/") |
[.sid, .url] | @csv' |
awk 'BEGIN{FS=","}{if($2~/http:\/\/blog\.gepuro\.net\/page/){cnt+=1}}END{print NR","cnt","cnt/NR}' |
header -a '"トップページからの遷移数","ページング数", "割合"'

echo

cat data/* |
jq -r '
select(.site=="blog.gepuro.net") |
select(.referrer == "http://blog.gepuro.net/") |
select(.url != "http://blog.gepuro.net/") |
[.sid, .url] | @csv' |
header -a '"sid","url"' |
q -H -O -d ',' '
select
url,
count(1) as pv_url
from -
group by url
order by 2 desc
limit 10
'

jqコマンド便利だなあ。

サイトのロゴ画像はクリックされるのか

一般的なwebサイトでは、タイトルのロゴ画像にトップページへのリンクを張っています。とは言え、これをクリックしてくれる人って、一体何人いるのだろうかと疑問に感じたので、調べてみました。

計測方法

ロゴ画像のリンクを「http://blog.gepuro.net/?from=logo」として、webビーコンを確認する。

JSONで保存しているので、jqコマンドやqコマンドを下のように使う。

cat data/* |
jq -r '
select(.site=="blog.gepuro.net") |
select(.unixtime >= 1450334421 and .unixtime <= 1452177993) |
[.sid, .url] | @csv' |
header -a '"sid","url"' |
q -H -O -d ',' '
select sid,
max(
case 
when url = "http://blog.gepuro.net/?from=logo" then 1 else 0
end
) as logo_flag
from -
group by sid
' |
q -H -O -d ',' '
select
count(1) as session_cnt,
sum(logo_flag) as click_logo_cnt,
1.0 * sum(logo_flag) / count(1) as click_logo_rate
from -
'

結果は、

session数 ロゴのクリック人数 ロゴのクリック率
635 10 0.016

となった。

ほぼ誰もクリックしないのかよ・・・。orz

twitter上の反応