web-dev-qa-db-ja.com

「KerasLSTMを理解する」に関する疑問

私はLSTMに不慣れで、 Keras LSTMを理解する を経験し、 Daniel Moller による美しい答えに関連するいくつかのばかげた疑問を持っていました。

ここに私の疑問のいくつかがあります:

  1. _Achieving one to many_セクションで指定されている2つの方法があり、_stateful=True_を使用して、1つのステップの出力を繰り返し取得し、それを次のステップの入力として使用できます(output_features == input_featuresが必要) 。

    _One to many with repeat vector_ダイアグラムでは、繰り返されるベクトルはすべてのタイムステップで入力として供給されますが、_One to many with stateful=True_では、出力は次のタイムステップで入力として供給されます。では、_stateful=True_を使用して、レイヤーの動作方法を変更しませんか?

    [〜#〜] rnn [を構築するときは、上記の2つのアプローチ(繰り返しベクトルOR前のタイムステップ出力を次の入力として供給する)のどちらを使用するか)に従う必要があります。 〜#〜]

  2. _One to many with stateful=True_セクションで、_one to many_の動作を変更するには、予測の手動ループのコードで、出力シーケンスの長さがわからないため、_steps_to_predict_変数をどのように知るのでしょうか。あらかじめ。

    また、モデル全体が_last_step output_を使用して_next_step ouput_を生成する方法も理解していませんでした。 model.predict()関数の動作について混乱しました。つまり、生成される_no. of output sequences_(まだ値がわからない)をループしてmodel.predict()を実行するのではなく、model.predict()が出力シーケンス全体を一度に同時に予測することはありません。特定の反復における特定のタイムステップ出力を予測しますか?

  3. _Many to many_のケース全体を理解できませんでした。他のリンクが役に立ちます。

  4. model.reset_states()を使用して、新しいバッチが前のバッチから独立していることを確認していることを理解しています。ただし、あるバッチが別のバッチに続くようにシーケンスのバッチを手動で作成するのか、それとも_stateful=True_モードでKerasがシーケンスをそのようなバッチに自動的に分割するのか。

    それが手動で行われる場合、なぜ誰かがデータセットをそのようなバッチに分割し、シーケンスの一部が1つのバッチにあり、他の部分が次のバッチにあるのでしょうか?

  5. 最後に、_stateful=True_が使用される実際の実装または例/ユースケースは何ですか(これは何か変わっているように見えるため)?私はLSTMを学んでおり、Kerasでstatefulを紹介するのはこれが初めてです。

KerasでのLSTMの実装を明確にするために、誰かが私のばかげた質問を説明するのを手伝ってくれますか?

編集:これらのいくつかに現在の答えの明確化を求め、いくつかに残りの疑問を求める

[〜#〜] a [〜#〜]。したがって、基本的にステートフルでは、バッチごとに内部状態を_keep OR reset_できます。次に、各バッチがトレーニングされた後、内部状態を何度もリセットし続けると、モデルはどのように学習しますか?リセットとは、(非表示状態の計算に使用される)パラメーターをリセットすることを本当に意味しますか?

[〜#〜] b [〜#〜]。行_If stateful=False: automatically resets inner state, resets last output step_。最後の出力ステップをリセットするとはどういう意味ですか?つまり、すべてのタイムステップが独自の出力を生成する場合、最後の出力ステップのリセットはどういう意味で、それも最後のステップだけですか?

[〜#〜] c [〜#〜]。 _Question 2_と_Question 4_の2番目のポイントに応答して、まだ_manipulate the batches between each iteration_とstateful((_Question 2_の最後の行)の必要性を取得できませんでした。状態)。タイムステップで生成されたすべての出力の入力がわからないという点に到達しました。

したがって、シーケンスを_only one-step_のシーケンスに分割してから、new_step = model.predict(last_step)を使用しますが、これを何度も繰り返す必要がある時間をどのようにして知ることができますか(ループの停止点が必要です) )?また、stateful部分(_Question 2_の最後の行)についても説明してください。

[〜#〜] d [〜#〜]。 _One to many with stateful=True_の下のコードでは、次のWordがテスト時に使用されることを予測するためにforループ(手動ループ)が使用されているようです。モデルは電車の時間にそれ自体を組み込んでいますか、それともmanuallyは電車の時間にもこのループを使用する必要がありますか?

[〜#〜] e [〜#〜]機械翻訳ジョブを実行しているとすると、入力(翻訳する言語)全体が入力タイムステップに入力され、出力(翻訳された言語)が生成された後にシーケンスの中断が発生すると思います)各タイムステップで_manual loop_を介して実行されます。これは、入力が終了し、反復を使用して各タイムステップで出力の生成を開始するためです。私はそれを正しく理解しましたか?

[〜#〜] f [〜#〜]。 LSTMのデフォルトの動作には、回答に記載されている3つのことが必要であるため、シーケンスが壊れた場合は、_current_input_と_previous_output_に同じベクトルが供給されます。これは、現在の入力が利用できない場合の値が同じ?

[〜#〜] g [〜#〜]stateful = Trueの下のPredicting:セクションの下で、コードは次のようになります。

_predicted = model.predict(totalSequences)
firstNewStep = predicted[:,-1:]
_

_finding the very next Word in the current sequence_の手動ループはこれまで使用されていなかったので、model.predict(totalSequences)によって予測されたタイムステップのcountをどのように知ることができるので、predicted( _predicted[:,-1:]_)は、後で残りのシーケンスを生成するために使用されますか?つまり、_manual for loop_(後で使用)の前にpredicted = model.predict(totalSequences)で生成されたシーケンスの数をどのように知ることができますか。

編集2:

[〜#〜] i [〜#〜]Dの回答では、モデルをどのようにトレーニングするのかまだわかりませんでしたか?手動ループ(トレーニング中)を使用すると非常に苦痛になる可能性があることを理解していますが、それを使用しない場合、_we want the 10 future steps, we cannot output them at once because we don't have the necessary 10 input steps_の状況でモデルはどのようにトレーニングされますか? model.fit()を使用するだけで問題は解決しますか?

[〜#〜] ii [〜#〜]D回答の最後のパラグラフ_You could train step by step using train_on_batch only in the case you have the expected outputs of each step. But otherwise I think it's very complicated or impossible to train._。

これについて詳しく説明していただけますか?

_step by step_はどういう意味ですか? 持っていない OR 持っている後のシーケンスの出力の場合、それはトレーニングにどのように影響しますか?それでも必要ですか?トレーニング中の手動ループ。そうでない場合、model.fit()関数は希望どおりに機能しますか?

[〜#〜] iii [〜#〜]。 _"repeat" option_を_repeat vector_を使用していると解釈しました。繰り返しベクトルを使用するのは、_one to many_の場合には適していませんが、_many to many_の場合には適していません。後者には、選択できる入力ベクトルが多数あるためです(単一の繰り返しベクトルとして使用されます)。 ? _repeat vector_の場合に_many to many_をどのように使用しますか?

12
AJ.S

質問3

質問を理解することは、他の人を理解するための一種の鍵なので、最初に試してみましょう。

Kerasのすべての繰り返しレイヤーはhiddenループを実行します。これらのループは私たちにはまったく見えませんが、各反復の結果を見ることができます最後に

目に見えない反復の数は、time_steps次元と同じです。したがって、LSTMの反復計算は、ステップに関して発生します。

Xステップで入力を渡すと、X個の非表示の反復が発生します。

LSTMの各反復は、次の3つの入力を取ります。

  • このステップの入力データのそれぞれのスライス
  • レイヤーの内部状態
  • 最後の反復の出力

したがって、次のサンプル画像を見てください。ここで、入力には5つのステップがあります。

many to many

Kerasは単一の予測で何をしますか?

  • ステップ0:
    • 入力の最初のステップであるinput_data[:,0,:](batch, 2)の形をしたスライスを実行します。
    • 内部状態を取ります(この時点ではゼロです)
    • 最後の出力ステップを実行します(最初のステップには存在しません)
    • 計算を次のように渡します:
      • 内部状態を更新します
      • 1つの出力ステップを作成します(出力0)
  • ステップ1:
    • 入力の次のステップを実行します:input_data[:,1,:]
    • 更新された内部状態を取得します
    • 最後のステップで生成された出力(出力0)を取得します
    • 同じ計算を次のように渡します:
      • 内部状態を再度更新する
      • もう1つの出力ステップを作成します(出力1)
  • ステップ2:
    • input_data[:,2,:]を取る
    • 更新された内部状態を取得します
    • 出力1を取得します
    • パススルー:
      • 内部状態を更新します
      • 出力2を作成します
  • 手順4まで続きます。

  • 最後に:

    • stateful=Falseの場合:内部状態を自動的にリセットし、最後の出力ステップをリセットします
    • stateful=Trueの場合:内部状態を保持し、最後の出力ステップを保持します

これらの手順は表示されません。 1回のパスのように見えます。

ただし、次のいずれかを選択できます:

  • return_sequences = True:すべての出力ステップが返されます。形状は(batch, steps, units)
    • これはまさに多対多です。入力と同じステップ数が出力に表示されます
  • return_sequences = False:最後の出力ステップのみが返されます。形状は(batch, units)
    • これは多対1です。入力シーケンス全体に対して単一の結果を生成します。

さて、これはあなたの質問2の2番目の部分に答えます:はい、predictはあなたが気付かないうちにすべてを計算します。だが:

出力ステップの数は、入力ステップの数と同じになります

質問4

さて、質問2に進む前に、実際に答えのベースである4を見てみましょう。

はい、バッチ分割を行う必要があります手動。 Kerasはバッチを変更しません。では、なぜシーケンスを分割したいのですか?

  • 1、シーケンスが大きすぎる、1つのバッチがコンピューターまたはGPUのメモリに適合しない
  • 2、あなたは質問2で起こっていることをしたい:各ステップの反復の間のバッチを操作します。

質問2

質問2では、「未来を予測する」ことです。では、出力ステップ数はいくつですか?さて、予測するのは必要な数です。過去に基づいてクライアントの数を予測しようとしているとします。将来の1か月、または10か月の予測を決定できます。あなたの選択。

さて、あなたはpredictが一度に全部を計算すると考えるのは正しいですが、私が言った上記の質問を覚えておいてください:

出力ステップの数は、入力ステップの数と同じです。

また、最初の出力ステップは最初の入力ステップの結果であり、2番目の出力ステップは2番目の入力ステップの結果であるというように注意してください。

しかし、私たちは未来を望んでいます。前のステップに1つずつ一致するものではありません。結果のステップが「最後の」ステップの後に続くようにします。

したがって、制限に直面します。それぞれの入力がない場合に、固定数の出力ステップを定義する方法は? (遠い未来へのインプットも未来なので、存在しません)

そのため、シーケンスを1ステップのみのシーケンスに分割します。したがって、predict1ステップのみを出力します。

これを行うと、各反復の間にバッチを操作することができます。また、出力データ(以前はなかった)を入力データとして受け取ることができます。

また、これらの各ステップを単一のシーケンスとして接続する必要があるため、ステートフルが必要です(状態を破棄しないでください)。

質問5

私が知っているstateful=Trueの最も実用的なアプリケーションは、質問2の答えです。ステップ間でデータを操作したいと思います。

これはダミーの例かもしれませんが、別のアプリケーションは、たとえばインターネット上のユーザーからデータを受信して​​いる場合です。ユーザーがWebサイトを使用する毎日、モデルにもう1ステップのデータを提供します(そして、このユーザーの以前の履歴を同じ順序で継続したい)。

質問1

次に、最後に質問1。

私は言うでしょう:あなたがそれを必要とするでない限り、常にstateful=Trueを避けてください。
1対多のネットワークを構築するために必要ないので、使用しない方がよいでしょう。

このためのstateful=Trueの例は、将来を予測するの例と同じですが、単一のステップから開始することに注意してください。実装するのは難しいです。手動ループのために速度が遅くなります。ただし、出力ステップの数を制御することはできます。これは、場合によっては必要なことかもしれません。

計算にも違いがあります。そしてこの場合、私は一方が他方よりも優れているかどうか本当に答えることができません。しかし、大きな違いはないと思います。しかし、ネットワークはある種の「芸術」であり、テストは面白い驚きをもたらすかもしれません。

編集のための回答:

A

「状態」を「重み」と間違えないでください。それらは2つの異なる変数です。

  • 重み:学習可能なパラメーター、それらはリセットされないです。 (重みをリセットすると、モデルが学習したすべてが失われます)
  • 状態:現在シーケンスのバッチのメモリ(現在のシーケンスのどのステップと、このステップまでに「このバッチの特定のシーケンスから」学んだことに関する)。

あなたが映画(シーケンス)を見ていると想像してください。毎秒、キャラクターの名前、彼らがしたこと、彼らの関係が何であるかなどの思い出を構築します。

今までに見たことのない映画を手に入れ、映画の最後の1秒を見始めると想像してみてください。この映画の前の話が必要なので、映画の終わりを理解することはできません。 (状態)

これで、映画全体を見終わった画像。これで、新しい映画(新しいシーケンス)の視聴を開始します。最後に見た映画で何が起こったのかを覚えておく必要はありません。 「映画に参加」しようとすると、混乱するでしょう。

この例では:

  • 重み:あなたの能力映画を理解して解釈する、能力重要な名前と行動を記憶する
  • 状態:一時停止した映画では、状態は最初から現在までに起こったことのメモリです。

したがって、状態は「学習されていません」。状態は「計算」され、バッチ内の個々のシーケンスに関して段階的に構築されます。それが理由です:

  • 状態をリセットするということは、ステップ0から新しいシーケンスを開始する(新しいムービーを開始する)ことを意味します。
  • 状態を維持するということは、最後のステップから同じシーケンスを継続することを意味します(一時停止された映画を継続するか、そのストーリーのパート2を視聴します)

状態は、リカレントネットワークを「過去のステップからのメモリ」があるかのように機能させるものです。

B

LSTMでは、最後の出力ステップは「状態」の一部です。

LSTM状態には次のものが含まれます。

  • 計算によってステップごとに更新されるメモリマトリックス
  • 最後のステップの出力

つまり、はい。すべてのステップで独自の出力が生成されますが、すべてのステップで最後のステップの出力が状態として使用されます。これがLSTMの構築方法です。

  • 同じシーケンスを「続行」する場合は、最後のステップの結果を記憶する必要があります
  • 新しいシーケンスを「開始」する場合は、最後のステップの結果のメモリは必要ありません(状態をリセットしない場合、これらの結果は保存されたままになります)

C

必要なときに停止します。将来、いくつのステップを予測しますか?それがあなたの停止点です。

20ステップのシーケンスがあると想像してください。そして、将来的には10歩を予測したいと思います。

標準の(ステートフルではない)ネットワークでは、次のものを使用できます。

  • 一度に19ステップ入力(0から18)
  • 一度に19ステップ出力(1から19)

これは「次のステップの予測」です(シフト= 1ステップに注意してください)。すべての入力データが利用可能であるため、これを行うことができます。

ただし、将来の10ステップが必要な場合、必要な10の入力ステップがないため、一度に出力することはできません(これらの入力ステップは将来であり、最初に予測するモデルが必要です)。

したがって、既存のデータから1つの将来のステップを予測し、このステップを次の将来のステップの入力として使用する必要があります。

しかし、私はこれらのステップがすべて接続されていることを望んでいます。 stateful=Falseを使用すると、モデルには多くの「長さ1のシーケンス」が表示されます。いいえ、長さ30のシーケンスが1つ必要です。

D

これは非常に良い質問であり、あなたは私を手に入れました..。

ステートフルな1対多は、その答えを書くときに私が持っていたアイデアでしたが、私はこれを使用したことはありませんでした。私は「リピート」オプションを好みます。

各ステップで期待される出力がある場合にのみ、train_on_batchを使用してステップバイステップでトレーニングできます。しかし、そうでなければ、訓練するのは非常に複雑または不可能だと思います。

E

これは一般的なアプローチの1つです。

  • ネットワークを使用して凝縮されたベクトルを生成します(このベクトルは、結果、生成された状態、またはその両方である可能性があります)
  • この凝縮されたベクトルを別のネットワークの初期入力/状態として使用し、手動で段階的に生成し、モデルによって「文の終わり」の単語または文字が生成されたときに停止します。

手動ループのない固定サイズのモデルもあります。あなたはあなたの文がX語の最大長を持っていると仮定します。これより短い結果の文は、「文の終わり」または「null」の単語/文字で補完されます。 Maskingレイヤーは、これらのモデルで非常に役立ちます。

F

入力のみを指定します。他の2つ(最後の出力と内部状態)は、すでにステートフルレイヤーに格納されています。

特定のモデルが次のステップを予測するであるという理由だけで、入力=最後の出力を作成しました。それが私たちが望んでいることです。入力ごとに、次のステップ。

トレーニングの順序を変えてこれを教えました。

G

それは問題ではありません。最後のステップだけが必要です。

  • シーケンスの数は、最初の:によって保持されます。
  • そして、最後のステップだけが-1:によって考慮されます。

ただし、知りたい場合は、predicted.shapeを印刷できます。このモデルではtotalSequences.shapeと同じです。

編集2

まず、「1対多」のモデルを使用して将来を予測することはできません。そのためのデータがないためです。シーケンスのステップのデータがない場合、「シーケンス」を理解する可能性はありません。

したがって、このタイプのモデルは、他のタイプのアプリケーションに使用する必要があります。前にも言ったように、私はこの質問に対する良い答えを本当に持っていません。最初に「目標」を設定してから、その目標に適したモデルの種類を決定することをお勧めします。

II

「ステップバイステップ」とは、手動ループを意味します。

後のステップの出力がなければ、トレーニングすることは不可能だと思います。それはおそらくまったく有用なモデルではありません。 (しかし、私はすべてを知っている人ではありません)

出力がある場合は、はい、手動ループを気にせずにfitを使用してシーケンス全体をトレーニングできます。

III

そして、あなたはIIIについて正しいです。入力データが変化するため、多対多で繰り返しベクトルを使用することはありません。

「1対多」と「多対多」は2つの異なる手法であり、それぞれに長所と短所があります。 1つは特定のアプリケーションに適し、もう1つは他のアプリケーションに適しています。

16
Daniel Möller