web-dev-qa-db-ja.com

Kerasで2つのシーケンシャルモデルをマージする

私はケラスで2つの連続したモデルをマージしようとしています。コードは次のとおりです。

_model1 = Sequential(layers=[
    # input layers and convolutional layers
    Conv1D(128, kernel_size=12, strides=4, padding='valid', activation='relu', input_shape=input_shape),
    MaxPooling1D(pool_size=6),
    Conv1D(256, kernel_size=12, strides=4, padding='valid', activation='relu'),
    MaxPooling1D(pool_size=6),
    Dropout(.5),

])

model2 = Sequential(layers=[
    # input layers and convolutional layers
    Conv1D(128, kernel_size=20, strides=5, padding='valid', activation='relu', input_shape=input_shape),
    MaxPooling1D(pool_size=5),
    Conv1D(256, kernel_size=20, strides=5, padding='valid', activation='relu'),
    MaxPooling1D(pool_size=5),
    Dropout(.5),

])

model = merge([model1, model2], mode = 'sum')
Flatten(),
Dense(256, activation='relu'),
Dropout(.5),
Dense(128, activation='relu'),
Dropout(.35),
# output layer
Dense(5, activation='softmax')
return model
_

エラーログは次のとおりです。

ファイル「/nics/d/home/dsawant/anaconda3/lib/python3.6/site-packages/keras/backend/tensorflow_backend.py」、392行目、is_keras_tensorのValueValue( 'Unexpectedly found type of instance of ' + str(type(x)) + '。 'ValueError:タイプ_<class 'keras.models.Sequential'>_のインスタンスが予期せず見つかりました。シンボリックテンソルインスタンスが必要です。

もう少しログ:

ValueError:レイヤーmerge_1は、シンボリックテンソルではない入力で呼び出されました。受信したタイプ:クラス 'keras.models.Sequential'。完全な入力:[keras.models.Sequential object at 0x2b32d518a780、keras.models.Sequential object at 0x2b32d521ee80]。レイヤーへのすべての入力はテンソルでなければなりません。

異なるウィンドウサイズを使用し、「max」、「sum」などの関数を適用するこれら2つのシーケンシャルモデルをマージするにはどうすればよいですか?

14
Digvijay Sawant

functional APIを使用すると、すべての可能性がもたらされます。

機能的なAPIを使用する場合、単にレイヤーを定義するのではなく、入力と出力を追跡する必要があります。

レイヤーを定義してから、入力テンソルでレイヤーを呼び出して出力テンソルを取得します。モデルとレイヤーはまったく同じ方法で呼び出すことができます。

マージレイヤーについては、Add()Multiply()Concatenate()など、より直感的な他のマージレイヤーを使用することを好みます。

from keras.layers import *

mergedOut = Add()([model1.output,model2.output])
    #Add() -> creates a merge layer that sums the inputs
    #The second parentheses "calls" the layer with the output tensors of the two models
    #it will demand that both model1 and model2 have the same output shape

この同じ考え方は、次のすべてのレイヤーに適用されます。出力テンソルを更新して各レイヤーに渡し、新しい出力を取得します(ブランチの作成に関心がある場合、関心のある出力ごとに異なるvarを使用してそれらを追跡します)。

mergedOut = Flatten()(mergedOut)    
mergedOut = Dense(256, activation='relu')(mergedOut)
mergedOut = Dropout(.5)(mergedOut)
mergedOut = Dense(128, activation='relu')(mergedOut)
mergedOut = Dropout(.35)(mergedOut)

# output layer
mergedOut = Dense(5, activation='softmax')(mergedOut)

「パス」を作成したので、Modelを作成します。モデルの作成は、どの入力テンソルで開始し、どこで終了するかを伝えるのと同じです。

from keras.models import Model

newModel = Model([model1.input,model2.input], mergedOut)
    #use lists if you want more than one input or output    

このモデルには2つの入力があるため、リスト内の2つの異なるX_training変数を使用してトレーニングする必要があることに注意してください。

newModel.fit([X_train_1, X_train_2], Y_train, ....)    

ここで、入力が1つだけで、model1とmodel2の両方が同じ入力を受け取ると仮定します。

機能的なAPIは、入力テンソルを作成し、それをモデルに渡すことで、非常に簡単にそれを可能にします(モデルをレイヤーであるかのように呼び出します)。

commonInput = Input(input_shape)

out1 = model1(commonInput)    
out2 = model2(commonInput)    

mergedOut = Add()([out1,out2])

この場合、モデルは次の入力を考慮します。

oneInputModel = Model(commonInput,mergedOut)
18
Daniel Möller