初めまして。
システムソリューション部の長田と申します。
昨今では「AI」や「Deep Learning」などのキーワードとともに、データ分析が注目されています。 データ分析を行うためのツールは数多く存在し、それらをインストールするには意外と手間がかかります。 特にDeep LearningのアルゴリズムをGPUで計算する際に使われるcuda周りのインストールはノウハウがないと面倒です。
本記事では、データ分析で用いる主要なツールがプレインストールされているAzureのデータサイエンス仮想マシン(DSVM)を使ってDeep Learningを行ってみた感想について書いていきます。
アウトライン
1. データサイエンス仮想マシンによる環境構築
2. 検証に使ったDeep Learningモデルの説明
3. 検証結果
4. 感想
5. 参考文献
6. 付録(グローバル注意機構の詳細説明)
1. データサイエンス仮想マシンによる環境構築
データサイエンス仮想マシンとは、その名の通り、データサイエンス専用にカスタマイズされたMicrosoftのAzure上にある仮想マシンのイメージです。
環境として用意されているOSは私が見つけた限りでは下記があるようです。
- Windows Server 2012
- Windows Server 2016
- Ubuntu 16.04 LTS
- CentOSベースのOpenLogic 7.2 (GPU未対応:2017年7月19日時点)
今回は個人的に使い慣れているUbuntuでDeep Learningを用いた検証を行いました。
下記のリンクへ移動して[GET IT NOW] (スクリーンショットの赤枠部分)をクリックします。
■Linux用データサイエンス仮想マシン(Ubuntu)へのリンク
https://azuremarketplace.microsoft.com/en-us/marketplace/apps/microsoft-ads.linux-data-science-vm-ubuntu

利用規約やプライバシーに関する声明に目を通し、[Continue]ボタンをクリックします。

しばらくすると、Azureへのログインが済んでいない場合はログイン、ログイン済みの場合はAzureのポータルに移動します。その後、[作成]をクリックします。

入力が求められた項目をそれぞれ入力していきます。
[VMディスクの種類]はGPUを利用する場合は、HDDを指定する必要がある点に注意してください。
[場所]はGPUを使う場合はNCシリーズやNVシリーズが使える場所を選択する必要がありますので、下記URLにて確認してご自分の目的に合わせて選択してください。
ちなみにDeep Learningに向いているのはNVIDIA Tesla K80が搭載されているNCシリーズです。
https://azure.microsoft.com/ja-jp/regions/services/
また、下記のURLでは2017年の後半にはPascalアーキテクチャのGPUを搭載したNDシリーズやNCv2シリーズがリリースされる予定であるとの記載があります。
https://azure.microsoft.com/en-us/blog/more-gpus-more-power-more-intelligence/
これらのシリーズは計算速度も現行シリーズの2倍以上の性能を発揮できるようですので、リリース後はこちらを利用するのも良いかもしれません。
全ての項目を入力したら[OK]をクリックします。
次にサイズの選択ですが、今回はNC6で検証をしていきますので、[サポートされるディスクの種類]が[HDD]になっていることを確認し、[すべて表示]をクリックします。
そして、NC6を選択して[OK]をクリックします。

あとは通常のAzureと同様にご自分の環境に合わせて項目を選択して、[OK]で進めていけば構築はできるかと思います。
利用する範囲に絞って、今回プレインストールされている環境について説明します。
anacondaがインストールされており、python2.7のrootとpython3系のpy35というconda環境が存在しています。今回はPython3.5を使うので、py35のconda環境を使います。
py35のconda環境に切り替えるには下記のコマンドを実行します。
$ source /anaconda/bin/activate py35
2017年7月19日時点では、Chainerがプレインストールされていないため、pipでインストールする必要があります。下記のMicrosoft社のニュースリリースでは2017年夏にはChainerが搭載される予定とのことなので、もうしばらくすれば搭載されるようです。
https://news.microsoft.com/ja-jp/2017/05/23/170523-azure-preferred-networks/#sm.0000d2wbquhunfisvp52mbsj8nhpr%23QTDP1sPdCiRTyksQ.97
Chainerのインストール
$ sudo /anaconda/envs/py35/bin/pip install chainer $ sudo /anaconda/envs/py35/bin/pip install cupy
また、今回はMeCabを使って日本語の分かち書きを行うため、インストールも行いました。
MeCabのインストール
$ sudo apt-get install mecab mecab-ipadic-utf8 $ sudo apt-get install libmecab-dev $ sudo /anaconda/envs/py35/bin/pip install mecab-python3
2. 検証に使ったDeep Learningモデルの説明
今回は動作までにかかる時間や使い心地を知りたかったため、少量の日本語と英語の対訳データ(1200文章)を使って、Encoder-Decoder翻訳モデルを用いた機械翻訳に挑戦してみました。
使用するアルゴリズムはBidirectional Long Short-Term Memory(Bidirectional LSTM)とGlobal Attention(グローバル注意機構)を用いたSequence to Sequence(Seq2Seq)です。
Bidirectional LSTMについて説明する前に、まずはRecurrent Neural Network(RNN)を簡単に説明いたします。
「単語を入力して、次の単語を予測する」というタスクを考えた時に、基本的な順伝播型ニューラルネットワークによる予測では、下図のように入力として単語のみを与えて学習しています。

この構造上、過去の文脈情報を予測に反映出来ないという課題がありました。
RNNは下記のように単語に加え、前の単語の予測に使った隠れ層のベクトルを入力として使う事でその課題を解決したものです。

今回は一般的によく用いられるLSTMと呼ばれるRNNの拡張モデルを使います。LSTM自体も色々な拡張をされていますが、検証に使ったのはメモリと入力ゲート、出力ゲート、忘却ゲートの3つのゲートから成るものです。 様々な方がLSTMについての解説は書いていますので、本記事では詳細については踏み込みません。下記がとても参考になりました。
【前編】深層学習による自然言語処理 – ニューラル機械翻訳への理論 –
Bidirectional LSTMとは、下記のように単語に加え、Forward LSTM(順方向LSTM)とBackward LSTM(逆方向LSTM)の隠れ層のベクトルを連結して入力として使うモデルの事です。文脈の過去の情報だけでなく、未来の情報も用いることができます。

Seq2Seqとは、Encoder-Decoderモデルの一種です。下図のように入力側のEncoderと出力側のDecoderの2つのRNNを用意して、中間層で繋いだネットワークの構造をしています。

Seq2Seqでは、英語の予測結果と学習データのギャップを損失と捉え、この損失を最小化していくように学習を進めていくという仕組みになっています。
ただ、Seq2Seqには翻訳に適応した際、入出力長が長くなるにつれて翻訳精度が下がっていくという問題がしばしば起こるようです。この問題を克服するために、注意機構を用いることがあります。
人間が文章を翻訳する時はおそらく翻訳時に関係しそうな重要な単語に注目しながら翻訳を行なっているかと思います。厳密に言えば違うと思いますが、これと似た機能を導入するための機構が注意機構です。
注意機構を使うことで、入力と出力の単語の対応付け(単語アライメント)の情報の翻訳への反映や可視化が可能になります。
このうち、グローバル注意機構はEncoder側の各隠れ層のベクトルの加重平均を計算することにより、文脈ベクトルを算出する機構です。下記の論文により提案されました。
NEURAL MACHINE TRANSLATION BY JOINTLY LEARNING TO ALIGN AND TRANSLATE
今回利用したグローバル注意機構では、下記の図のように双方向LSTMを用いる場合、順方向の文脈ベクトルと逆順方向の文脈ベクトルをそれぞれ求める仕組みになっています。
仕組みの詳細については「6. 付録(グローバル注意機構の詳細説明)」に記しましたので、ここでは省略します。
このグローバル注意機構により算出した文脈ベクトルを用いて、Decoderに予測させることにより、長文の翻訳精度の改善が期待できます。
注意機構にはグローバル注意機構以外にもローカル注意機構など様々な機構が提案されておりますが、今回はグローバル注意機構の一部の提案のみを取り上げて紹介いたしました。
3. 検証結果
では、翻訳を試してみましょう。
今回はCPUとGPUでの計算速度の違いを見るためにそれぞれの実行時間を見てみました。本実験では最適化のアルゴリズムはAdam、パラメータはデフォルト値を使っています。
実際に翻訳してみるのは次の5つの文章についてです。
■翻訳するデータ一覧
- 今何を話しているの?
- お会いできて嬉しいです
- ご機嫌いかがでしょうか?
- 大丈夫、彼はおとなしいよ
- こんにちは
これらの文章は「こんにちは」と「お会いできて嬉しいです」と「ご機嫌いかがでしょうか?」は同じデータが学習データに含まれていますが、「今何を話しているの?」と「大丈夫、彼はおとなしいよ」については学習データに含まれていません。
今回は下記4つの設定でそれぞれ翻訳精度と実行時間を検証してみました。
実験番号 | 端末 | CPU/GPU | バッチサイズ | 単語の埋め込みユニット数 | 隠れ層のユニット数 | Epoch数 |
---|---|---|---|---|---|---|
1 | Mac book Air | CPU | 50 | 200 | 200 | 150 |
2 | Mac book Air | CPU | 50 | 1000 | 1000 | 150 |
3 | データサイエンス仮想マシン | NC6 GPU | 50 | 200 | 200 | 150 |
4 | データサイエンス仮想マシン | NC6 GPU | 50 | 1000 | 1000 | 150 |
■ 実験番号1の結果
今何を話しているの? => what are you going to has about here ?
お会いできて嬉しいです => much is the cake .
ご機嫌いかがでしょうか? => would you he ?
大丈夫、彼はおとなしいよ => i found up got her .
こんにちは => hello.
実行時間: 45分38秒
翻訳は「こんにちは」以外は正解できておらず、全体的にあまり良くない精度になっているように見受けられます。
■ 実験番号2の結果
今何を話しているの? => what are you cooking ?
お会いできて嬉しいです => it’s a pleasure to meet you .
ご機嫌いかがでしょうか? => how are you ? ! ! !
大丈夫、彼はおとなしいよ => wherever he would you please check this matter of fact
こんにちは => hello.
実行時間: 7時間36分49秒
「お会いできて嬉しいです」と「こんにちは」は上手く翻訳できています。また、「ご機嫌いかがでしょうか」については何やら惜しいものが出ました。
■ 実験番号3の結果
今何を話しているの? => what are you talking about ?
お会いできて嬉しいです => it’s a pleasure to meet you .
ご機嫌いかがでしょうか? => how heavy i this ?
大丈夫、彼はおとなしいよ => hi .
こんにちは => hello .
実行時間:40分21秒
「ご機嫌いかがでしょうか」と「大丈夫、彼はおとなしいよ」以外については良い翻訳をしているように見受けられます。
■ 実験番号4の結果
今何を話しているの? => what are you talking about ?
お会いできて嬉しいです => it’s a pleasure to meet you .
ご機嫌いかがでしょうか? => how are you ?
大丈夫、彼はおとなしいよ => as is often the case with her, she broke
こんにちは => hello . she is a taxi .
実行時間:53分08秒
「大丈夫、彼はおとなしいよ」や「こんにちは」以外については良い翻訳をしてくれています。
実行時間についてまとめると、下記のようになりました。

この結果を見たところ、どうやらユニット数が多くないとあまりGPUの恩恵を受けられないようです。
Seq2Seqでは学習データにない未知語を含む文章については上手く予測できませんでした。こちらについてはデータを増やすか、未知語が出現した時に何かしらの対策をとるのが一般的のようです。
他にも学習データに存在している文章についても、epochが足りないのか、上手く翻訳できないこともありました。epochが150程度だと学習も途中で打ち切られてしまっているようで、もっとepochを増やすべきであったと反省しています。
4. 感想
最後にAzureのデータサイエンス仮想マシン(DSVM)を使ってみた感想です。
筆者は、Azureを使ったDeep Learningの高速化を行うのは初めてでしたが、このデータサイエンス仮想マシンを使うと、簡単に環境構築とGPUを利用することができました。
このように環境構築という面倒な部分が楽になっていけば、その分の時間が分析に当てられるので、分析環境や計算資源が必要な方は一度使ってみてはいかがでしょうか。
5. 参考文献
今回の検証では、下記のURLや書籍を参考にしました。
■ Azure関連
Introducing the new Data Science Virtual Machine on Windows Server 2016
Linux および Windows 用のクラウド ベースのデータ サイエンス仮想マシンの概要
■ 技術関連
深層学習による自然言語処理(機械学習プロフェッショナルシリーズ)
今更ながらchainerでSeq2Seq(2)〜Attention Model編〜
【前編】深層学習による自然言語処理 – ニューラル機械翻訳への理論
Effective Approaches to Attention-based Neural Machine Translation
Attention and Memory in Deep Learning and NLP
最近のDeep Learning (NLP) 界隈におけるAttention事情
6. 付録(グローバル注意機構の詳細説明)
それぞれの文脈ベクトルの具体的な計算は、下図の流れで行っています。

この図では、Encoderの1単語目以外の計算は同様の計算を行うため、省略しています。
 : 順方向Encoderの隠れ層のベクトルを同じサイズのベクトルを出力する線形結合層
: 逆方向Encoderの隠れ層のベクトルを同じサイズのベクトルを出力する線形結合層
: Decoderの隠れ層のベクトルと同じサイズのベクトルを出力する線形結合層
: 隠れ層のサイズからサイズ1のスカラーを出力する線形結合層
: 入力されたベクトルの足し算
: 入力されたベクトルのかけ算
矢印の色は青が文脈ベクトルの算出に直接関係がないデータのやり取り、赤がsoftmaxを通すまでの経路と逆順方向の文脈ベクトルを求める経路、黒が順方向の文脈ベクトルを求める経路、緑枠は計算の順番を示しています。
計算の流れをまとめますと、下記の通りとなります。(図の緑枠の①から⑥と対応づけしています)
① 順方向のEncoderの隠れ層、逆順方向のEncoderの隠れ層、予測元のDecoderの隠れ層のベクトルをそれぞれ線形結合したものの総和を求める
② ①の計算結果をtanh関数に入力して、-1から1の間のベクトルを得る
③ ②の計算結果を線形結合して、スカラー値に変換する
④ ③の計算結果とSoftmax関数に入力して、正規化を行う。
⑤ ④の計算結果と順方向のEncoderの隠れ層ベクトル、④の計算結果と逆順方向のEncoderの隠れ層ベクトルをそれぞれのペア同士掛けたものをそれぞれ求める。
⑥ 順方向のEncoderの隠れ層ベクトルをかけた方の⑤の計算結果の総和を求めると、順方向の文脈ベクトルが算出される。同様に逆順方向のEncoderの隠れ層ベクトルをかけた方の⑤の計算結果の総和を求めることで、逆順方向の文脈ベクトルを求める。