简体   繁体   中英

What should my input to a keras conv1D layer be and what should the input_shape be?

Note: First time posting. I've tried to be thorough in my description

I've been trying to set up what I thought would be a very simple CNN by following this tutorial: https://machinelearningmastery.com/cnn-models-for-human-activity-recognition-time-series-classification/

My Xtrain dataset is a time series as a numpy array with 34396 rows (samples) and 600 columns (time steps). My Ytrain dataset is just an array containing labels 0,1, or 2 (as ints). I'm just trying to use the CNN to perform multi-classification.

I'm running into an issue getting errors like

Input 0 is incompatible with layer conv1d_39: expected ndim=3, found ndim=4

when input_shape=(n_timesteps,n_features,n_outputs)

or

Error when checking input: expected conv1d_40_input to have 3 dimensions, but got array with shape (34396, 600)

when input_shape=(n_timesteps,n_features)

I've been searching online for hours now but I can't seem to find a solution to my problem. I think its a simple problem with my data format and the input_shape values but I haven't been able to fix it.

I've tried setting input_shape to

(None, 600, 1)
(34396,600, 1)
(34396,600)
(None,600)

among various other combinations.

train_df = pd.read_csv('training.csv')
test_df = pd.read_csv('test.csv')

x_train=train_df.iloc[:,2:].values
y_train=train_df.iloc[:,1].values
x_test=train_df.iloc[:,2:].values
y_test=train_df.iloc[:,1].values
n_rows=len(x_train)
n_cols=len(x_train[0])

def evaluate_model(trainX, trainy, testX, testy):
    verbose, epochs, batch_size = 0, 10, 32
    n_timesteps, n_features, n_outputs = trainX.shape[0], trainX.shape[1], 3
    print(n_timesteps, n_features, n_outputs)
    model = Sequential()
    model.add(Conv1D(filters=64, kernel_size=3, activation='relu', input_shape=(n_timesteps,n_features,n_outputs)))
    model.add(Conv1D(filters=64, kernel_size=3, activation='relu'))
    model.add(Dropout(0.5))
    model.add(MaxPooling1D(pool_size=2))
    model.add(Flatten())
    model.add(Dense(100, activation='relu'))
    model.add(Dense(n_outputs, activation='softmax'))
    model.compile(loss='categorical_crossentropy', optimizer='adam', metrics=['accuracy'])
    # fit network
    model.fit(trainX, trainy, epochs=epochs, batch_size=batch_size, verbose=verbose)
    # evaluate model
    _, accuracy = model.evaluate(testX, testy, batch_size=batch_size, verbose=0)
    return accuracy
evaluate_model(x_train,y_train,x_test,y_test)

As given in the keras doc , for Conv1D , for example input_shape=(10, 128) for time series sequences of 10 time steps with 128 features per step.

So for your case since you have 600 timesteps each of 1 feature it should be input_shape=(600,1) .

Also you have to feed your labels y 's as one-hot-encoded.

Working code

from keras.utils import to_categorical

model = Sequential()
model.add(Conv1D(filters=64, kernel_size=3, activation='relu', input_shape=(600,1)))    
model.add(Conv1D(filters=64, kernel_size=3, activation='relu'))
model.add(Dropout(0.5))
model.add(MaxPooling1D(pool_size=2))
model.add(Flatten())
model.add(Dense(100, activation='relu'))
model.add(Dense(10, activation='softmax'))
model.compile(loss='categorical_crossentropy', 
              optimizer='adam', metrics=['accuracy'])

x = np.random.randn(100,600)
y = np.random.randint(0,10, size=(100))
# Reshape to no:of sample, time_steps, 1 and convert y to one hot encoding
model.fit(x.reshape(100,600,1), to_categorical(y))
# Same as model.fit(np.expand_dims(x, 2), to_categorical(y))

Output:

Epoch 1/1
100/100 [===========================] - 0s 382us/step - loss: 2.3245 - acc: 0.0800

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM