読者です 読者をやめる 読者になる 読者になる

Itsukaraの日記

最新IT技術を勉強・実践中。最近はDeep Learningに注力。

Tensorboardのグラフは、もうすこし何とかならないのか?

機械学習 ITのお勉強 Python

Tensorflowでは、ゲームSCOREなどのスカラ値をTensorboardでグラフ化してくれるのはありがたいのですが、グラフが荒すぎます。また、移動平均など、当然必要と思われる機能がありません。

せめて、移動平均ぐらいは出して欲しいです。試しに、ゲームSCOREとその移動平均を表示するプログラムを作ってみました。

下記が、試作プログラムの表示画面です。緑の線は、100サンプルでの移動平均を表示しています。青いものは、線ではなく、点の集まりであり、スカラ値そのものをプロットしています。横軸は、globalなstep数で、縦軸はreward(この場合、BreakoutのゲームSCORE)です。
f:id:Itsukara:20160731193227p:plain

ちなみに、下記は、Tensorboardの表示画面です。かなり差がありますよね。特に、Tensoboardでは、3000000 stepあたりから移動平均が上昇カーブになっている部分が、全くわかりません。何とかして欲しいです。

f:id:Itsukara:20160731193357p:plain

なお、スカラ値は、学習中に自前で出力するようにしました。

しょぼいですが、下記が表示プログラムです。データは、CSV形式で入っており、X軸とY軸をどのカラムにするか指定できます。デフォルトは、それぞれ1と2です。ちなみに、カラムは0から始まる設定です。

import numpy as np
import argparse
import matplotlib.pyplot as plt
from operator import itemgetter

parser = argparse.ArgumentParser(description="plot data in csv file")
parser.add_argument('filename')
parser.add_argument('-x', '--x-column', type=int, default=1,
                    help="column index of x-axis (0 origin)")
parser.add_argument('-y', '--y-column', type=int, default=2,
                    help="column index of y-axis (0 origin)")
parser.add_argument('-a', '--average-number-of-samples', dest="ans", type=int, default=100,
                    help="average number of samples")
parser.add_argument('-s', '--scale', type=float, default=1e6,
                    help="scale factor: data in x-column is divided by SCALE")
parser.add_argument('-xl', '--xlabel', default="M steps",
                    help="label of x-axis")
parser.add_argument('-yl', '--ylabel', default="Score",
                    help="label of y-axis")

args = parser.parse_args()

data = np.genfromtxt(args.filename, delimiter=",", dtype=np.float)

# sort data along args.x_column and make it np.array again
data = sorted(data, key=itemgetter(args.x_column))
data = np.array(data)

x = data[:, args.x_column]
y = data[:, args.y_column]
x = x / args.scale
plt.plot(x, y, ',')

weight = np.ones(args.ans, dtype=np.float)/args.ans
y_average = np.convolve(y, weight, 'valid')
header = np.ones(args.ans - 1) * y_average[0]
y_average = np.hstack((header, y_average))
plt.plot(x, y_average)

plt.xlabel(args.xlabel)
plt.ylabel(args.ylabel)
plt.grid()

plt.show()

こんな短いプログラムでも、それなりの表示はできるので、Googleは出し惜しみせずにもう少し良い物を出して欲しいです。

追記

上記ではグリッド線が表示されず、さすがにわかりにくいので、グリッド線を追加しました(plt.grid())。

また、もう少し先までTrainingした図も参考までに下記に載せます。Tenworflowは折れ線で、分布の広がりを表現しているように見ますが、細かなところがわかりません。自ミニプログラムでは、データの分布と平均がよくわかると思います。

  • 自作ミニプログラムで作成したグラフ

データの分布状況と、その平均がよくわかります。ただ、平均自体も、かなり変化が激しいですね。なお、縦軸が800までありますが、これは、700点を超えるデータが1つだけあるためです。図をクリックして拡大してよ〜く見ると、右端の730点のところに点が1つあります(かなり見難いで、手作業で赤丸を追加しました)。
f:id:Itsukara:20160801080425p:plain

  • Tensorflowのグラフ

折れ線グラフが上下に激しく変化し、どこが平均なのかわかりません。ただ、改めて自作プログラムのグラフと比較すると、データの分散が広い部分は、このように折れ線を激しく変化させて表現しているようにも見えますね。この表現では平均の変化がわからないのが一番の難点です。
f:id:Itsukara:20160801074308p:plain