Как сформировать 2-элементные входные данные для LSTM - PullRequest
2 голосов
/ 23 мая 2019

Я использую RNN с узлами LSTM в Keras для прогнозирования временных рядов. У меня есть две функции ввода и одна функция вывода, и я использую скользящее окно размера 4 и размера шага 1.

Итак, я пытаюсь подготовить массивы соответственно для LSTM для обработки данных. Тем не менее, размеры не кажутся правильными. Я получил его до такой степени, что я получил трехмерный массив в правильной форме для сети, чтобы принять его, но способ настройки данных в массиве мне не кажется правильным.

Итак, глядя только на тренировочные данные, это необработанные данные из файла:

train_input = df[['a','b']].values (this is of shape (354, 2))
train_output = df[['c']].values (this is of shape (354, 1))

Далее я масштабирую данные, после чего форма остается прежней. И затем я хочу использовать цикл, чтобы привести данные в форму скользящего окна (размер окна 4, диапазон 354):

train_input_window = []
train_output_window = []
for i in range(4, 354):
   train_input_window.append(train_input_scaled[i-4:i, 0])   
   train_input_window.append(train_input_scaled[i-4:i, 1])  
   train_output_window.append(train_output_scaled[i, 0])
train_input_window = np.array(train_input_window)
train_output_window = np.array(train_output_window)

Теперь train_input_window имеет форму (700, 4) и train_output_window имеет форму (350,)

Так вот в чем проблема, я думаю. Потому что я могу преобразовать данные в трехмерный массив, который будет работать:

train_input3D = np.reshape(train_input_window, (350,4,2))
train_output3D = np.reshape(train_output_window, (350,1,1))

но я просто не думаю, что данные правильно расположены внутри массивов. тренировочный вклад выглядит примерно так:

print(train_input3D)
[[[a a]
  [a a]
  [b b]
  [b b]]

 [[a a]
  [a a]
  [b b]
  [b b]].....

не должно быть

[[[a b]
  [a b]
  [a b]
  [a b]]

 [[a b]
  [a b]
  [a b]
  [a b]].....

Я пробовал так много разных вещей, и к настоящему времени я настолько растерян, что просто надеюсь, что я не смущаю здесь всех, пытаясь объяснить.

Итак, форма ввода, которая, по моему мнению, должна соответствовать моему массиву для того, что я пытаюсь? Если так, то как мне это устроить? Вот мой полный код:

#Read Data
df = pd.ExcelFile('GPT.xlsx').parse('7Avg')

# Training Data
train_input = df[['Precip_7Sum','Temp_7Avg']].values#
train_output = df[['GWL_7Avg']].values

# Testing Data
test_input = df[['Precip_7SumT','Temp_7AvgT']].values#
test_output = df[['GWL_7AvgT']].values

# normalize / scale Data
input_scaler = MinMaxScaler(feature_range = (0, 1))
output_scaler = MinMaxScaler(feature_range = (0, 1))

train_input_scaled = input_scaler.fit_transform(train_input) 
train_output_scaled = output_scaler.fit_transform(train_output)
test_input_scaled = input_scaler.transform(test_input)
test_output_scaled = output_scaler.transform(test_output)

# Convert Data into sliding window format
train_input_window = [] 
train_output_window = []  
for i in range(4, 354):      
   train_input_window.append(train_input_scaled[i-4:i, 0])   
   train_input_window.append(train_input_scaled[i-4:i, 1])  
   train_output_window.append(train_output_scaled[i, 0])
train_input_window = np.array(train_input_window)
train_output_window = np.array(train_output_window)

test_input_window = []  
test_output_window = []  
for i in range(4, 354):  
   test_input_window.append(train_input_scaled[i-4:i, 0])
   test_input_window.append(train_input_scaled[i-4:i, 1])
   test_output_window.append(train_output_scaled[i, 0])
test_input_window = np.array(test_input_window) 
test_output_window = np.array(test_output_window)

# Convert data into 3-D Formats
train_input3D = np.reshape(train_input_window, (350,train_input_window.shape[1],2)) # 3D tensor with shape (batch_size, timesteps, input_dim) // (nr. of samples, nr. of timesteps, nr. of features)
train_output3D = np.reshape(train_output_window, (350,1,1)) # 

test_input3D = np.reshape(test_input_window, (350,test_input_window.shape[1],2))

# Instantiate model class
model = Sequential()

# Add LSTM layer
model.add(LSTM(units=1, return_sequences = True, input_shape = (4,2)))

# Add dropout layer to avoid over-fitting 
model.add(Dropout(0.2))

# add three more LSTM and Dropouts
model.add(LSTM(units=1, return_sequences=True))  
model.add(Dropout(0.2))

model.add(LSTM(units=1, return_sequences=True))  
model.add(Dropout(0.2))

model.add(LSTM(units=1, return_sequences=True))  
model.add(Dropout(0.2))

# Create dense layer at the end of the model to make model more robust
model.add(Dense(units = 1, output_shape = (4,1)))

# Compile model
model.compile(optimizer = 'adam', loss = 'mean_squared_error')

# Training
model.fit(train_input3D, train_output_window, epochs = 100, batch_size = 4)

# Testing / predictions
train_predictions = model.predict(train_input3D)
test_predictions = model.predict(test_input3D)

# Reverse scaling of data for output data
train_predictions = input_scaler.inverse_transform(train_predictions)
test_predictions = input_scaler.inverse_transform(test_predictions)
orig_data = train_output.append(test_output)

Любая помощь по этому вопросу будет высоко ценится. Я надеюсь, что смогу достаточно ясно изложить свою проблему, и что кто-то, кто мог бы помочь, действительно прочитает все это: D

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...