2017-12-11 週の日記

12/11(月)~12/17(日)の日記を書きます。

参加したイベント

第10回 強化学習アーキテクチャ勉強会 - connpass(12/12)
  • スライドがアップされていました: GAN(と強化学習との関係)
  • 生成モデルって何だったっけ; 生成モデルは日本人の顔が出てくる箱。逆にこの箱をつくるには日本人の顔のデータが要る。生成モデルをつくるときに、「特徴量をニューラルネットに入れて出てくるものを取り出す」というやり方でつくろうとするのが VAE や GAN。ただし両者はこの箱の学習の仕方が異なる。
    • VAEは入力と出力の差が小さくなるようにエンコーダ+デコーダを学習して、デコーダに適当な値を入力すると模造データが出てくる。
      • ところでVAEは特徴量がガウス分布であることまで求めるのでしたっけ。
    • GANでは、まずジェネレータ  G が乱数から模造データを生成して、ディスクリミネータ  D がそれを模造データかどうか純正データか識別する。それを受けてジェネレータはディスクリミネータに純正データと識別してもらえるように模造データを純粋データに近づける。ディスクリミネータはそれでも識別できるようにする。その繰り返し。
      • MCMC のようだと思った; MCMC でいう標本分布=模造データの分布で、MCMCでいう真の分布=純正データの分布。
  • JSダイバージェンス
  • 課題:  D が未熟だと、 G は同じような模造データばかりつくってしまう。なので、 D の性能を十分上げておきたいが、といって完璧にしてしまうと、 G はネットワークの重みをどの方向に更新しても損失が変わらなくなってしまい、学習できなくなる。
  • 純正データは純正データ空間のとても局所的なところにしか存在しないので、 G がもともと上手い模造データをつくらないとほぼ交わらないというのも MCMC に似ている。それを解決するのがワッサースタイン距離。
  • GAN がよいかどうかの評価は、GANをつかう目的に照らし合わせてだと思った(GANそのものの研究についての論文ではもちろんGANだけで評価することが必要ですが)。
  • アクター・クリティックについて昔作成したスライド(この前頁が REINFORCE):
  • 強化学習でいう「期待収益をよくすること」と GAN にとっての「純正データっぽい模造データを出すこと」はどうアナロジーなのか。強化学習での方策の期待収益を見極める=GANの真贋を見極めるで、よい方策を求める=精巧な模造品をつくるで、訊こうと思ったけどまあいいや。
Speee もくもく会(12/16)

また昼食をいただきました。ありがとうございました。

mockmock.dev #142 - connpass(12/17)

遅刻してしまいました。ありがとうございました。

2017-12-04 週の日記

最近雑記ばかりで雑すぎるので週次の日記にしようと思います。12/4(月)~12/10(日)の日記にしようと思いますがついでなのでその前の週のことも一緒に書きます。

読んだ記事

GitHub - NVIDIA/sentiment-discovery: Unsupervised Language Modeling at scale for robust sentiment classification
  • テキストを単語列ではなく文字列として学習してセンチメント分類しても上手くいくという話(辞書を作成しないから Unsupervised?)。
  • 単語列ではなく文字列として扱うことで、capitalized/uncaptilized の取り扱いを明示的に与えなくていいし、ミススペルにも対応できるし、未知語にも対応できる。
  • でも英語は26文字しかないけど日本語は平仮名、片仮名、漢字がたくさんあるけど上手くいくのだろうか。
Interpretable Machine Learning
  • 機械学習モデルを解釈可能にするという話。GitHub Pages で作成してあるようなので自分もいつかこういうのを書きたいなあ。
  • model-agnostics: モデルに依存しない(という意味でいいのですよね?)
[1712.02029] AdaBatch: Adaptive Batch Sizes for Training Deep Neural Networks
  • SGDによる深層ニューラルネットの最適化は学習率とバッチサイズを慎重に選ぶ必要がある。バッチサイズが小さい方が少ないエポック数で収束するけどバッチサイズが大きい方がたくさん並列計算できるので計算効率がいい。なのでエポックを経るごとにバッチサイズを大きくしていくことで、小さい固定バッチサイズ並のエポック数で大きい固定バッチサイズ並の計算効率を達成しましたという話(?)。

参加したイベント

第9回 強化学習アーキテクチャ勉強会 - connpass(11/28)
  • この勉強会の中で、紹介された高次行動を抽象化する解法だとベルマン最適方程式の解より高い報酬が得られるのかという質問があって、得られるのではないかというやり取りがあったのですが、それを聞いていて、報酬が高くなるのではなくてよりよい解にたどり着く確率とか収束の速さがよくなるのではないかなと思ったんですが、オンライン学習なら確かによくなるのかなと思いました(オンライン学習の解ってどこなんですけど)。よくわかりません。
  • オプションのサブゴールは所与ということだったのですが、サブゴールもタスクから決める論文もあるとかおっしゃっていたのですが、もっとちゃんと訊けばよかったです。
Gunosyデータマイニング研究会 #132 - connpass(11/29)
  • 分散未知の場合の共役事前分布がなんでウィシャート分布じゃなくて逆ガンマ分布なのかと思ったのですが、共分散行列を  \sigma^2 I に決め打っているからで、でも共分散行列が  \sigma^2 I って何だろう、予測対象変数が各要素が独立の確率値とかだったらそんな状況もあるのだろうかと思いました。
Speee もくもく会 #31 - connpass(12/2)
  • 朝食も昼食もご馳走になってしまいました…なんかすみません…。
朝もくもく会@神田橋 - connpass(12/7)
  • もくもく会を主催してみたのですが誰も来ませんでした。逆に来たらびっくりするんでそれはいいんですけど、1時間というのはどうにも短いと思いました。30分単位で借りられれば30分延ばしたいんですが。もっとアクセスがよさそうな神田駅前にも貸し会議室を見つけましたが、神田駅に寄るのが面倒なので次もここでやります。
mockmock.dev #141 - connpass(12/10)
  • Slack 上のもくもく会に参加させていただきました。実は冒頭50分昼食作って食べてました。すみません…。

その他

来週やりたいこと

  • GitHub Pages をせっかくつくったので、週の日記にはその週に読んだことを、GitHub Pages にはその蓄積を配置したいですが、フォルダ以下に記事群を置いたら PythonPerl で各記事にリンクを張った HTML を生成するようにしたい(そんなことをやっているので文献読みが進みません)。

雑記: GitHub Pages で自分のノート(HTML)をつくる

気になったウェブ上の記事や論文をまとめて自分用に知識を構造化したいですが、紙のノートは後からカットペーストして整理するのに不向きだし、ブログは構造がブログだし、Qiita は他の人に役立つことを意識したものだし記事をずっとインクリメントしていくものでもないと思います。あと自宅からも会社からも閲覧したいのと、Contributions Calendar が面白そうなので GitHub をつかってみたいと思います。

GitHub 上に自分のノートをつくる
  • 手元の Win 機に Git がインストールされていなかったのでまずインストールする。
  • GitHubリポジトリをつくる。
    • https://github.com/ にアカウント名とメールアドレスとパスワードを入れる。
    • メールがくるのでリンクをクリックしてメールアドレスを Verify する。
    • 遷移した画面の右上の + マークから New Repository をクリックする。
    • リポジトリ名だけ入れる。最初なので test にしました。無料版だと非公開にはできない。
  • ローカルリポジトリをつくって GitHub リポジトリと関連付ける。
    • 最初は空コミットでいいや。 空コミットは何故か失敗したので、test.md というファイルを add して commit した。いきなりコミットすると Git に「あなたはどこの誰?」と訊かれるので、画面の指示通りにメールアドレスとアカウント名を教えてあげる(でも push 時に確認ダイアログが出てまた訊かれた)。
      git init
      git add test.md
      git status -suno
      git config --global user.email xxxxx@xxx.com
      git config --global user.name CookieBox26
      git commit -m "first commit"
      git log
      git remote add origin https://github.com/CookieBox26/test.git
      git push -u origin master
      test.md
      # ほげ

      ## ふが

      ここに本文を書く。
    • そうすると test.md が GitHub の自分のページからでHTML化されて見えます。これにどんどん自分のノートを書いていけばよさそうな気がします。
GitHub Pages をつかってみる
  • これで作業の土台はできましたが、push するまでマークダウンがプレビューできないのは不便です。Markdown Previewer で検索すると以下のサイトがあり、マークダウン記法はこれで確認できそうです。
    Markdown Editor
  • でもツールでマークアップさせながらの作業は面倒です。個人的には HTML タグ打ちも苦にならないというかタグ打ちの方が思い通りの表現ができるので、HTML ファイル(できればその階層構造も)を直接コミットしてそれをウェブ上から閲覧できないだろうかと思います。→ 試しに適当な test.html を作成してコミットしてみましたが、これだけではテキスト表示されるのみでした。
  • どうしようかと思っていると以下のページを見つけます。
    GitHub Pages を使った静的サイトの公開方法が、とても簡単になっていた | Tips Note by TAM
    このページにしたがってリポジトリを静的サイト化します。上の記事で設定する Setting は画面の一番右上の + メニューの Setting ではなくて、特定のリポジトリを表示したときの一番右側のタブです。ここで master branch を選択して Save を押すと、ページがここに公開されましたよという URL が表示されると思います。
    https://CookieBox26.github.io/test
    • このとき、先ほどコミットした test.html のファイル名を index.html に rename しました。
    • 余計なファイルがあると URL が表示される代わりに「余計なファイルがある」というエラーが表示されます。今回は test.md を削除しました。
    • また、HTML ファイルのエンコードUTF-8 にする必要があります。SJIS で作成したために日本語が文字化けしていたのでこれも直しました(コミットからサイトへの反映に少々時間がかかるようなので、反映されない場合はまず少し待ってみてください)。
これで安心してノートを蓄積できるね

蓄積しないと意味ないね。

雑記

Qiita に投稿しましたが、後半文字だらけで見づらいのと、肝心なHTMLソース部分の説明がないので後日絵や解説を入れるなどリファクタリングできたらいいなあと思います。qiita.com
後半文字だらけで見づらいですが、この分野を知らない人にもわかるようにどのような仮定を置いているかをきちんと書こうとしています。それで肝心の二項ツリーの説明までたどり着けていないんですが、二項ツリーで置いている仮定は既に説明している「無裁定条件」「無リスク金利で貸し借りができる相手の存在」に加えて、

  • 時間  \Delta t だけ先に株価は今より  u 倍に上がるか  d 倍に下がるかの2択とする(から二項ツリーになるのですが)。
  •  ud =1 とする。
  •  \Delta t の1次以上の項は無視できるとする。

辺りになると思います。そうなると株価のボラティリティ  \sigma と矛盾しないように  u d が決まります。このとき二項ツリーによるオプション価格の求め方は以下の手順になります。

  • 満期日までの時間をじゅうぶん細かい  \Delta t ずつに区切る。
  • ツリーの根元のノードに現在の株価  S_0 を記入し、 u 倍や  d 倍しながら末端のノードまで株価を埋める。
  • 次に、株価の下にオプション価格を書いていく。ツリーの末端のノードについては容易に埋まる(例えばコール・オプションであれば行使価格  K として  \max (S_T-K, 0) を書き入れるだけ)。
  • 末端ではないノードのオプション価格については以下の手順で書き入れる。
    • 2つの子ノードを見て「どちらの未来になろうとも同じ価格になる、株とオプションからなるポートフォリオ」を構成する。
    • そのポートフォリオは無リスクなので、親ノードでのそのポートフォリオの価格は無裁定条件より決定する。
    • 親ノードの株価は既に埋まっているので、親ノードでのオプション価格を得る。

この要領で一番根元まで戻ってこれれば現在時点でのオプション価格が求まります。気分転換で数理ファイナンスの記事を書いてみましたが、次以降は統計や機械学習の記事を書きたいです。


それで、どのような仮定を置いているかをきちんとしたいと書いたのですが、少し前に twitter で話題になっていた(少し前というより定期的に話題になっているようですが)以下の確率の問題は仮定が足りない例です(文章は意訳です)。
Aさんには子どもが2人います。Aさんに「子どもたちに女の子はいますか?」と訊いたところAさんは「はい」と答えました。もう1人が女の子である確率はいくらでしょう。
「情報が足りない」「解釈による」といえばそれまでですが、どのように仮定を補うとどのように解けるのかを考えてみるのも面白いと思います。以下の1番下の図は答えが 1/3 となる考え方の1つの例です。ここで置いている仮定は、

  • Aさんに質問する前の子どもの性別の組合せの事前分布を P(男男)=P(男女)=P(女男)=P(女女)=0.25 とする。
  • 「もう1人」とは、女の子が少なくとも1人いると判明した後に、女の子を1人選び、残ったもう1人のこととする。

の2つになります。この問題でよく「こう解釈できるのでは?」争点になっているのは後者ですが、自分がどう解釈したかによって「このように仮定する」とすれば大丈夫です。それより前者について、「男女が生まれる確率が同じとする」のように表現しようとする回答が見受けられますが、その表現は以下の可能性を否定しないので同値ではないです。「独立な」とまでいうと1つ目の可能性のみ排除できますが、2~4つ目の可能性は残るのでやはり不十分です。

  • 第1子と第2子の性別に相関がある可能性。
  • 子どもが男でも女でもない性別である可能性。
  • 子どもの性別が出生後に変化する可能性。
  • Aさんに質問する前からAさんの子どもの性別の情報を(部分的に)知っている可能性。

この問題を「1/2 と 1/3 の2通りの解釈がある」と結論付ける回答もあるのですが、2通りどころか、仮定によって 0~1 のどの値にもなります。それどころか、Aさんの2人の子どもの性別の組合せの確率分布について事前に本当に全く何もわからないという立場を取るならば、1人が女の子だとわかったところでもう1人については「やはり何もわからない」という回答もあると思います。だから何なのかというと、「男女の出生率は等しく第n子にかかわらず独立」というのは、数理ファイナンスにおける「裁定機会は存在しない」「無リスク金利で貸し借りができる」などと似ていて、それなりには現実に近く、いつの間にかそれが当然のように受け入れがちな仮定なのですが(?)、厳密には成り立たないので、いつ仮定が利用されたかを把握していないと危ういんじゃないかな(まあ男女の出生率やその相関を厳密に考える場面などたぶん訪れないんですけど)という回りくどい話でした。

f:id:cookie-box:20171002221943p:plain

Keras で特定の軸方向に softmax したい

Keras で特定の軸方向に softmax したいときとかあると思います。

f:id:cookie-box:20170815221557p:plain:w720

Keras のドキュメントによるとどの軸に沿って正規化するかを指定する axis というのを渡せるようです。
Activations - Keras Documentation
ただ、渡し方がよくわかりません。以下の箇所に axis=2 と書いてもエラーになります。

from keras.models import Sequential
from keras.layers import Dense, Reshape, Activation

if __name__ == '__main__':
  model = Sequential()
  model.add(Dense(3*4*5, activation='relu', input_shape=(10,)))
  model.add(Reshape((3, 4, 5)))
  model.add(Activation('softmax', axis=2)) # ERROR
  model.compile(loss='mean_squared_error', optimizer='rmsprop')
  print(model.summary())

しょうがないので softmax をするだけの自作レイヤーをつくります。これはエラーになりません。

from keras.engine.topology import Layer
from keras.models import Sequential
from keras.layers import Dense, Reshape
from keras.activations import softmax

# いまやりたい softmax をするためだけのレイヤー
class MySoftmax(Layer):
  def __init__(self, **kwargs):
    super(MySoftmax, self).__init__(**kwargs)
  def call(self, x):
    return(softmax(x, axis=2))

if __name__ == '__main__':
  model = Sequential()
  model.add(Dense(3*4*5, activation='relu', input_shape=(10,)))
  model.add(Reshape((3, 4, 5)))
  model.add(MySoftmax())
  model.compile(loss='mean_squared_error', optimizer='rmsprop')
  print(model.summary())

本当に希望の軸方向に正規化されているか確認してみます。何でもよいので適当な入力を流し込めばよいです。

  x, y = [], []
  # 1だらけの適当なデータ
  for i in range(20):
    x.append(numpy.ones((10)))
    y.append(numpy.ones((3,4,5)))
  x = numpy.array(x)
  y = numpy.array(y)
  
  model.fit(x, y)
  y_test = model.predict(x)
  print(y_test[0])
[[[ 0.21292862  0.24584062  0.2997719   0.15851443  0.25      ]
  [ 0.30612475  0.24584062  0.22358862  0.32254457  0.25      ]
  [ 0.16930516  0.24584062  0.22358862  0.25293246  0.25      ]
  [ 0.31164148  0.26247811  0.25305092  0.26600859  0.25      ]]

 [[ 0.18996513  0.24999966  0.18364088  0.25715023  0.3020851 ]
  [ 0.23858465  0.25000107  0.27690381  0.21845251  0.27901751]
  [ 0.25863758  0.24999966  0.35581443  0.30594474  0.19078693]
  [ 0.31281266  0.24999966  0.18364088  0.21845251  0.22811046]]

 [[ 0.21095483  0.36942184  0.22160934  0.2253582   0.24394487]
  [ 0.26182058  0.22892946  0.22160934  0.32392535  0.24394487]
  [ 0.31626979  0.159567    0.335172    0.2253582   0.24394487]
  [ 0.21095483  0.24208161  0.22160934  0.2253582   0.26816541]]]

出力の shape が (3, 4, 5) で、axis=2 としたので、5つの要素の和を取る方向がこれで正規化されて…いません。
和が1になったのは4つの要素の和を取る方向でした。
axis=1, 2, 3 についてどの軸の方向が正規化されるのか調べると以下でした。5つの要素の和を取る方向を正規化したかったら axis=3 とすべきようです。

f:id:cookie-box:20170815225335p:plain:w750

axis=0, -1 のときは以下でした。axis=0 は 4x5 の面内の和が1になりました。axis=-1 はむしろ当初やりたかった softmax が達成されていました。-1 はデフォルトのはずで、じゃあわざわざカスタムレイヤつくる必要なかったのでしょうか。
f:id:cookie-box:20170815230442p:plain:w500

これでやりたい softmax ができたので、今度はこの softmax に合わせた cross entropy を用意しなくては、と思っているのですがもしかしてそれもわざわざやらなくてよいのでしょうか。