CNTK-シーケンス分類

この章では、CNTKのシーケンスとその分類について詳しく学習します。

テンソル

CNTKが機能するコンセプトは tensor。基本的に、CNTKの入力、出力、およびパラメーターは次のように編成されます。tensors、これは一般化されたマトリックスと見なされることがよくあります。すべてのテンソルにはrank

  • ランク0のテンソルはスカラーです。

  • ランク1のテンソルはベクトルです。

  • ランク2のテンソルはamatrixです。

ここでは、これらの異なる寸法は axes.

静的軸と動的軸

名前が示すように、静的軸はネットワークの存続期間を通じて同じ長さです。一方、動的軸の長さはインスタンスごとに異なる可能性があります。実際、それらの長さは通常、各ミニバッチが提示される前にはわかりません。

動的軸は、テンソルに含まれる数値の意味のあるグループ化も定義するため、静的軸に似ています。

明確にするために、短いビデオクリップのミニバッチがCNTKでどのように表されるかを見てみましょう。ビデオクリップの解像度がすべて640 * 480であると仮定します。また、クリップは通常3つのチャネルでエンコードされるカラーで撮影されます。さらに、ミニバッチには次のものがあることを意味します-

  • それぞれ長さ640、480、3の3つの静的軸。

  • 2つの動的軸。ビデオの長さとミニバッチ軸。

これは、ミニバッチにそれぞれ240フレームの長さの16本のビデオがある場合、次のように表されることを意味します。 16*240*3*640*480 テンソル。

CNTKでのシーケンスの操作

最初に長短期記憶ネットワークについて学習して、CNTKのシーケンスを理解しましょう。

長短期記憶ネットワーク(LSTM)

長短期記憶(LSTM)ネットワークは、Hochreiter&Schmidhuberによって導入されました。これにより、基本的な繰り返しレイヤーに長い間物事を記憶させるという問題が解決されました。LSTMのアーキテクチャは、上の図に示されています。ご覧のとおり、入力ニューロン、メモリセル、出力ニューロンがあります。勾配消失問題と戦うために、長短期記憶ネットワークは明示的記憶セル(以前の値を格納)と次のゲートを使用します-

  • Forget gate−名前が示すように、以前の値を忘れるようにメモリセルに指示します。メモリセルは、ゲート、つまり「ゲートを忘れる」が値を忘れるように指示するまで値を格納します。

  • Input gate −名前が示すように、セルに新しいものを追加します。

  • Output gate −名前が示すように、出力ゲートは、セルから次の非表示状態にベクトルを渡すタイミングを決定します。

CNTKでシーケンスを操作するのは非常に簡単です。次の例の助けを借りてそれを見てみましょう-

import sys
import os
from cntk import Trainer, Axis
from cntk.io import MinibatchSource, CTFDeserializer, StreamDef, StreamDefs,\
   INFINITELY_REPEAT
from cntk.learners import sgd, learning_parameter_schedule_per_sample
from cntk import input_variable, cross_entropy_with_softmax, \
   classification_error, sequence
from cntk.logging import ProgressPrinter
from cntk.layers import Sequential, Embedding, Recurrence, LSTM, Dense
def create_reader(path, is_training, input_dim, label_dim):
   return MinibatchSource(CTFDeserializer(path, StreamDefs(
      features=StreamDef(field='x', shape=input_dim, is_sparse=True),
      labels=StreamDef(field='y', shape=label_dim, is_sparse=False)
   )), randomize=is_training,
   max_sweeps=INFINITELY_REPEAT if is_training else 1)
def LSTM_sequence_classifier_net(input, num_output_classes, embedding_dim,
LSTM_dim, cell_dim):
   lstm_classifier = Sequential([Embedding(embedding_dim),
      Recurrence(LSTM(LSTM_dim, cell_dim)),
      sequence.last,
      Dense(num_output_classes)])
return lstm_classifier(input)
def train_sequence_classifier():
   input_dim = 2000
   cell_dim = 25
   hidden_dim = 25
   embedding_dim = 50
   num_output_classes = 5
   features = sequence.input_variable(shape=input_dim, is_sparse=True)
   label = input_variable(num_output_classes)
   classifier_output = LSTM_sequence_classifier_net(
   features, num_output_classes, embedding_dim, hidden_dim, cell_dim)
   ce = cross_entropy_with_softmax(classifier_output, label)
   pe =      classification_error(classifier_output, label)
   rel_path = ("../../../Tests/EndToEndTests/Text/" +
      "SequenceClassification/Data/Train.ctf")
   path = os.path.join(os.path.dirname(os.path.abspath(__file__)), rel_path)
   reader = create_reader(path, True, input_dim, num_output_classes)
input_map = {
   features: reader.streams.features,
   label: reader.streams.labels
}
lr_per_sample = learning_parameter_schedule_per_sample(0.0005)
progress_printer = ProgressPrinter(0)
trainer = Trainer(classifier_output, (ce, pe),
sgd(classifier_output.parameters, lr=lr_per_sample),progress_printer)
minibatch_size = 200
for i in range(255):
   mb = reader.next_minibatch(minibatch_size, input_map=input_map)
trainer.train_minibatch(mb)
   evaluation_average = float(trainer.previous_minibatch_evaluation_average)
   loss_average = float(trainer.previous_minibatch_loss_average)
return evaluation_average, loss_average
if __name__ == '__main__':
   error, _ = train_sequence_classifier()
   print(" error: %f" % error)
average  since  average  since  examples
loss     last   metric   last
------------------------------------------------------
1.61    1.61    0.886     0.886     44
1.61     1.6    0.714     0.629    133
 1.6    1.59     0.56     0.448    316
1.57    1.55    0.479      0.41    682
1.53     1.5    0.464     0.449   1379
1.46     1.4    0.453     0.441   2813
1.37    1.28     0.45     0.447   5679
 1.3    1.23    0.448     0.447  11365

error: 0.333333

上記のプログラムの詳細な説明は、特にリカレントニューラルネットワークを構築するときに、次のセクションで説明します。