RNN (Recurrent Neural Network) Tutorial: TensorFlow Eksempel

Hvorfor har vi brug for et tilbagevendende neuralt netværk (RNN)?

Recurrent Neural Network (RNN) giver dig mulighed for at modellere hukommelsesenheder til at bevare data og modellere kortsigtede afhængigheder. Det bruges også i tidsserieprognoser til identifikation af datakorrelationer og -mønstre. Det hjælper også med at producere prædiktive resultater for sekventielle data ved at levere lignende adfærd som en menneskelig hjerne.

Strukturen af ​​et kunstigt neuralt netværk er relativt enkel og handler hovedsageligt om matrixmultiplikation. I løbet af det første trin multipliceres inputs med initialt tilfældige vægte, og bias transformeres med en aktiveringsfunktion, og outputværdierne bruges til at lave en forudsigelse. Dette trin giver en idé om, hvor langt netværket er fra virkeligheden.

Den anvendte metrik er tabet. Jo højere tabsfunktion, jo dummere er modellen. For at forbedre kendskabet til netværket kræves der en vis optimering ved at justere nettets vægte. Den stokastiske gradientnedstigning er den metode, der anvendes til at ændre vægtens værdier i den rigtige retning. Når justeringen er foretaget, kan netværket bruge endnu en batch af data til at teste sin nye viden.

Fejlen er heldigvis lavere end før, men alligevel ikke lille nok. Optimeringstrinnet udføres iterativt, indtil fejlen er minimeret, dvs. der ikke kan udtrækkes mere information.

Problemet med denne type model er, at den ikke har nogen hukommelse. Det betyder, at input og output er uafhængige. Modellen er med andre ord ligeglad med, hvad der kom før. Det rejser nogle spørgsmål, når du skal forudsige tidsserier eller sætninger, fordi netværket skal have information om de historiske data eller tidligere ord.

For at løse dette problem er der udviklet en ny type arkitektur: Recurrent Neural Network (RNN herefter)

Hvad er et tilbagevendende neuralt netværk (RNN)?

A Recurrent Neural Network (RNN) er en klasse af Kunstigt neuralt netværk hvor forbindelsen mellem forskellige noder danner en rettet graf for at give en tidsmæssig dynamisk adfærd. Det hjælper med at modellere sekventielle data, der stammer fra feedforward-netværk. Det fungerer på samme måde som menneskelige hjerner til at levere forudsigelige resultater.

Et tilbagevendende neuralt netværk ligner et traditionelt neuralt netværk, bortset fra at en hukommelsestilstand tilføjes til neuronerne. Beregningen for at inkludere en hukommelse er enkel.

Forestil dig en simpel model med kun én neuron, der fødes af en batch af data. I et traditionelt neuralt net producerer modellen outputtet ved at gange inputtet med vægten og aktiveringsfunktionen. Med en RNN sendes dette output tilbage til sig selv et antal gange. Vi ringer tidstrin den tid, outputtet bliver input til den næste matrixmultiplikation.

For eksempel, på billedet nedenfor, kan du se netværket er sammensat af en neuron. Netværket beregner matrixmultiplikationen mellem input og vægt og tilføjer ikke-linearitet med aktiveringsfunktionen. Det bliver udgangen ved t-1. Dette output er input til den anden matrixmultiplikation.

Recurrent Neural Network (RNN)
Recurrent Neural Network (RNN)

Nedenfor koder vi en simpel RNN i TensorFlow for at forstå trinnet og også formen på outputtet.

Netværket er sammensat af:

  • Fire indgange
  • Seks neuroner
  • 2-gange trin

Netværket fortsætter som vist på billedet nedenfor.

Recurrent Neural Network (RNN)

Netværket kaldes 'tilbagevendende', fordi det udfører den samme operation i hver aktiveret firkant. Netværket beregnede vægten af ​​input og det tidligere output før for at bruge en aktiveringsfunktion.

import numpy as np
import tensorflow as tf
n_inputs = 4
n_neurons = 6
n_timesteps = 2
The data is a sequence of a number from 0 to 9 and divided into three batches of data.
## Data 
X_batch = np.array([
        [[0, 1, 2, 5], [9, 8, 7, 4]], # Batch 1
        [[3, 4, 5, 2], [0, 0, 0, 0]], # Batch 2
        [[6, 7, 8, 5], [6, 5, 4, 2]], # Batch 3
    ])

Vi kan bygge netværket med en pladsholder for data, det tilbagevendende trin og output.

  1. Definer pladsholderen for dataene
X = tf.placeholder(tf.float32, [None, n_timesteps, n_inputs])

Her:

  • Ingen: Ukendt og vil tage størrelsen på batchen
  • n_timesteps: Antal gange netværket vil sende output tilbage til neuronen
  • n_inputs: Antal input pr. batch
  1. Definer det tilbagevendende netværk

Som nævnt på billedet ovenfor er netværket sammensat af 6 neuroner. Netværket vil beregne produkt med to prikker:

  • Inputdata med det første sæt vægte (dvs. 6: lig med antallet af neuroner)
  • Tidligere output med et andet sæt vægte (dvs. 6: svarende til antallet af output)

Bemærk, at under den første feedforward, er værdierne af det forrige output lig med nuller, fordi vi ikke har nogen værdi tilgængelig.

Objektet til at bygge et RNN er tf.contrib.rnn.BasicRNNCell med argumentet num_units for at definere antallet af input

basic_cell = tf.contrib.rnn.BasicRNNCell(num_units=n_neurons)

Nu hvor netværket er defineret, kan du beregne output og tilstande

outputs, states = tf.nn.dynamic_rnn(basic_cell, X, dtype=tf.float32)

Dette objekt bruger en intern sløjfe til at gange matricerne det passende antal gange.

Bemærk, at det tilbagevendende neuron er en funktion af alle input fra de foregående tidstrin. Sådan bygger netværket sin egen hukommelse. Oplysningerne fra forrige gang kan forplante sig i fremtidig tid. Dette er magien ved tilbagevendende neurale netværk

## Define the shape of the tensor
X = tf.placeholder(tf.float32, [None, n_timesteps, n_inputs])
## Define the network
basic_cell = tf.contrib.rnn.BasicRNNCell(num_units=n_neurons)
outputs, states = tf.nn.dynamic_rnn(basic_cell, X, dtype=tf.float32)
init = tf.global_variables_initializer()
init = tf.global_variables_initializer()
with tf.Session() as sess:
    init.run()
    outputs_val = outputs.eval(feed_dict={X: X_batch})
print(states.eval(feed_dict={X: X_batch}))
[[ 0.38941205 -0.9980438   0.99750966  0.7892596   0.9978241   0.9999997 ]
 [ 0.61096436  0.7255889   0.82977575 -0.88226104  0.29261455 -0.15597084]
 [ 0.62091285 -0.87023467  0.99729395 -0.58261937  0.9811445   0.99969864]]

Til forklaringsformål udskriver du værdierne for den tidligere tilstand. Outputtet trykt ovenfor viser output fra den sidste tilstand. Udskriv nu alt output, du kan bemærke, at tilstandene er det forrige output for hver batch. Det vil sige, at det forrige output indeholder informationen om hele sekvensen.e

print(outputs_val)    
print(outputs_val.shape)    
[[[-0.75934666 -0.99537754  0.9735819  -0.9722234  -0.14234993
   -0.9984044 ]
  [ 0.99975264 -0.9983206   0.9999993  -1.         -0.9997506
   -1.        ]]

 [[ 0.97486496 -0.98773265  0.9969686  -0.99950117 -0.7092863
   -0.99998885]
  [ 0.9326837   0.2673438   0.2808514  -0.7535883  -0.43337247
    0.5700631 ]]

 [[ 0.99628735 -0.9998728   0.99999213 -0.99999976 -0.9884324
   -1.        ]
  [ 0.99962527 -0.9467421   0.9997403  -0.99999714 -0.99929446
   -0.9999795 ]]]
(3, 2, 6)

Recurrent Neural Network (RNN)

Outputtet har formen (3, 2, 6):

  • 3: Antal partier
  • 2: Nummer på tidstrinnet
  • 6: Antal neuroner

Optimeringen af ​​et tilbagevendende neuralt netværk er identisk med et traditionelt neuralt netværk. Du vil se mere detaljeret, hvordan du koder optimering i den næste del af denne tutorial om tilbagevendende neuralt netværk.

Ansøgninger af RNN

RNN har flere anvendelser, især når det kommer til at forudsige fremtiden. I den finansielle industri kan RNN være behjælpelig med at forudsige aktiekurser eller tegnet på aktiemarkedets retning (dvs. positiv eller negativ).

RNN er nyttigt for en autonom bil, da det kan undgå en bilulykke ved at forudse køretøjets bane.

RNN er meget brugt i tekstanalyse, billedtekstning, sentimentanalyse og maskinoversættelse. For eksempel kan man bruge en filmanmeldelse til at forstå den følelse, tilskueren opfattede efter at have set filmen. Automatisering af denne opgave er meget nyttig, når filmselskabet ikke har tid nok til at gennemgå, mærke, konsolidere og analysere anmeldelserne. Maskinen kan udføre arbejdet med en højere grad af nøjagtighed.

Begrænsninger af RNN

I teorien formodes RNN at bære informationen op til tider. Det er dog ret udfordrende at udbrede al denne information, når tidstrinnet er for langt. Når et netværk har for mange dybe lag, bliver det utræneligt. Dette problem kaldes: forsvindende gradientproblem. Hvis du husker det, opdaterer det neurale netværk vægten ved hjælp af gradient descent-algoritmen. Gradienterne bliver mindre, når netværket går ned til lavere lag.

Som konklusion forbliver gradienterne konstante, hvilket betyder, at der ikke er plads til forbedringer. Modellen lærer af en ændring i gradienten; denne ændring påvirker netværkets output. Men hvis forskellen i gradienten er for lille (dvs. vægten ændrer sig lidt), kan netværket ikke lære noget, og så outputtet. Derfor kan et netværk, der står over for et forsvindende gradientproblem, ikke konvergere mod en god løsning.

Forbedring LSTM

For at overvinde det potentielle problem med forsvindende gradient, som RNN står over for, forbedrede tre forskere, Hochreiter, Schmidhuber og Bengio RNN med en arkitektur kaldet Long Short-Term Memory (LSTM). Kort sagt giver LSMT netværket relevant tidligere information til nyere tid. Maskinen bruger en bedre arkitektur til at vælge og transportere information tilbage til senere tid.

LSTM-arkitektur er tilgængelig i TensorFlow, tf.contrib.rnn.LSTMCell. LSTM er uden for selvstudiets omfang. Du kan henvise til embedsmanden dokumentation for mere information

RNN i tidsserier

I denne TensorFlow RNN-tutorial skal du bruge en RNN med tidsseriedata. Tidsserier er afhængige af tidligere tid, hvilket betyder, at tidligere værdier inkluderer relevant information, som netværket kan lære af. Ideen bag forudsigelse af tidsserier er at estimere den fremtidige værdi af en serie, lad os sige aktiekurs, temperatur, BNP og så videre.

Dataforberedelsen til Keras RNN og tidsserier kan være en lille smule vanskelig. Først og fremmest er målet at forudsige den næste værdi af serien, hvilket betyder, at du vil bruge den tidligere information til at estimere værdien ved t + 1. Etiketten er lig med inputsekvensen og flyttet en periode frem. For det andet sættes antallet af input til 1, dvs. én observation pr. gang. Endelig er tidstrinnet lig med rækkefølgen af ​​den numeriske værdi. For eksempel, hvis du indstiller tidstrinnet til 10, vil inputsekvensen returnere ti på hinanden følgende gange.

Se på grafen nedenfor, vi har repræsenteret tidsseriedata til venstre og en fiktiv inputsekvens til højre. Du opretter en funktion til at returnere et datasæt med tilfældig værdi for hver dag fra januar 2001 til december 2016

# To plot pretty figures
%matplotlib inline
import matplotlib
import matplotlib.pyplot as plt
import pandas as pd
def create_ts(start = '2001', n = 201, freq = 'M'):
    rng = pd.date_range(start=start, periods=n, freq=freq)
    ts = pd.Series(np.random.uniform(-18, 18, size=len(rng)), rng).cumsum()
    return ts
ts= create_ts(start = '2001', n = 192, freq = 'M')
ts.tail(5)

Produktion

2016-08-31    -93.459631
2016-09-30    -95.264791
2016-10-31    -95.551935
2016-11-30   -105.879611
2016-12-31   -123.729319
Freq: M, dtype: float64
ts = create_ts(start = '2001', n = 222)

# Left
plt.figure(figsize=(11,4))
plt.subplot(121)
plt.plot(ts.index, ts)
plt.plot(ts.index[90:100], ts[90:100], "b-", linewidth=3, label="A training instance")
plt.title("A time series (generated)", fontsize=14)

# Right
plt.subplot(122)
plt.title("A training instance", fontsize=14)
plt.plot(ts.index[90:100], ts[90:100], "b-", markersize=8, label="instance")
plt.plot(ts.index[91:101], ts[91:101], "bo", markersize=10, label="target", markerfacecolor='red')
plt.legend(loc="upper left")
plt.xlabel("Time")

plt.show()

RNN i tidsserien

Den højre del af grafen viser alle serier. Det startede fra 2001 og slutter i 2019. Det giver ingen mening at fodre alle data i netværket, i stedet skal du oprette en batch af data med en længde svarende til tidstrinnet. Denne batch vil være X-variablen. Y-variablen er den samme som X, men forskudt med én periode (dvs. du ønsker at forudsige t+1).

Begge vektorer har samme længde. Du kan se det i højre del af ovenstående graf. Linjen repræsenterer de ti værdier af X-inputtet, mens de røde prikker er de ti værdier af etiketten, Y. Bemærk, at etiketten starter en periode foran X og slutter en periode efter.

Byg en RNN til at forudsige tidsserier i TensorFlow

Nu i denne RNN-træning er det tid til at bygge dit første RNN til at forudsige serien ovenfor. Du skal angive nogle hyperparametre (modellens parametre, dvs. antal neuroner osv.) for modellen:

  • Antal input: 1
  • Tidstrin (vinduer i tidsserier): 10
  • Antal neuroner: 120
  • Antal output: 1

Dit netværk vil lære af en sekvens på 10 dage og indeholde 120 tilbagevendende neuroner. Du fodrer modellen med ét input, dvs. én dag. Du er velkommen til at ændre værdierne for at se, om modellen er blevet bedre.

Før du konstruerer modellen, skal du opdele datasættet i et togsæt og testsæt. Det fulde datasæt har 222 datapunkter; du skal bruge de første 201 point til at træne modellen og de sidste 21 point til at teste din model.

Når du har defineret et tog- og testsæt, skal du oprette et objekt, der indeholder batchene. I denne batches har du X-værdier og Y-værdier. Husk, at X-værdierne er en periode forsinket. Derfor bruger du de første 200 observationer og tidstrinnet er lig med 10. X_batches objektet skal indeholde 20 batches af størrelsen 10*1. y_batches har samme form som X_batches objektet, men med en periode forud.

Trin 1) Opret toget og test

Først og fremmest konverterer du serien til en bedøvet matrix; derefter definerer du vinduerne (dvs. antallet af gange netværket vil lære af), antallet af input, output og størrelsen på togsættet som vist i TensorFlow RNN-eksemplet nedenfor.

series = np.array(ts)
n_windows = 20   
n_input =  1
n_output = 1
size_train = 201

Derefter opdeler du simpelthen arrayet i to datasæt.

## Split data
train = series[:size_train]
test = series[size_train:]
print(train.shape, test.shape)
(201,) (21,)

Trin 2) Opret funktionen til at returnere X_batches og y_batches

For at gøre det nemmere kan du oprette en funktion, der returnerer to forskellige arrays, en for X_batches og en for y_batches.

Lad os skrive en RNN TensorFlow-funktion til at konstruere batchene.

Bemærk, at X-batcherne er forsinket med én periode (vi tager værdien t-1). Funktionens output skal have tre dimensioner. De første dimensioner svarer til antallet af partier, den anden størrelsen af ​​vinduerne og den sidste er antallet af input.

Den vanskelige del er at vælge datapunkterne korrekt. For X-datapunkterne vælger du observationerne fra t = 1 til t =200, mens du for Y-datapunktet returnerer observationerne fra t = 2 til 201. Når først du har de rigtige datapunkter, er det ligetil at omforme serien.

For at konstruere objektet med batcherne skal du opdele datasættet i ti batches af samme længde (dvs. 20). Du kan bruge omformningsmetoden og sende -1, så serien svarer til batchstørrelsen. Værdien 20 er antallet af observationer pr. batch og 1 er antallet af input.

Du skal gøre det samme trin undtagen for etiketten.

Bemærk, at du skal flytte dataene til det antal gange, du vil prognose. For eksempel, hvis du vil forudsige én tid frem, så flytter du serien med 1. Hvis du vil forudse to dage, skal du flytte dataene med 2.

x_data = train[:size_train-1]: Select all the training instance minus one day
X_batches = x_data.reshape(-1, windows, input): create the right shape for the batch e.g (10, 20, 1)
def create_batches(df, windows, input, output):
    ## Create X         
        x_data = train[:size_train-1] # Select the data
        X_batches = x_data.reshape(-1, windows, input)  # Reshape the data 
    ## Create y
        y_data = train[n_output:size_train]
        y_batches = y_data.reshape(-1, windows, output)
        return X_batches, y_batches

Nu hvor funktionen er defineret, kan du kalde den for at oprette batcherne som vist i nedenstående RNN-eksempel.

X_batches, y_batches = create_batches(df = train,
                                      windows = n_windows,
                                      input = n_input,
                                      output = n_output)

Du kan udskrive formen for at sikre dig, at dimensionerne er korrekte.

print(X_batches.shape, y_batches.shape)
(10, 20, 1) (10, 20, 1)

Du skal oprette testsættet med kun én batch af data og 20 observationer.

Bemærk, at du forudsiger dage efter dage, betyder det, at den anden forudsagte værdi vil være baseret på den sande værdi af den første dag (t+1) af testdatasættet. Faktisk vil den sande værdi være kendt.

Hvis du ønsker at forudsige t+2 (dvs. to dage frem), skal du bruge den forudsagte værdi t+1; hvis du skal forudsige t+3 (tre dage frem), skal du bruge den forudsagte værdi t+1 og t+2. Det giver mening, at det er svært at forudsige præcist t+n dage frem.

X_test, y_test = create_batches(df = test, windows = 20,input = 1, output = 1)
print(X_test.shape, y_test.shape)
(10, 20, 1) (10, 20, 1)

Okay, din batchstørrelse er klar, du kan bygge RNN-arkitekturen. Husk, du har 120 tilbagevendende neuroner.

Trin 3) Byg modellen

For at oprette modellen skal du definere tre dele:

  1. Variablen med tensorerne
  2. RNN
  3. Tabet og optimeringen

Trin 3.1) Variabler

Du skal angive X- og y-variablerne med den passende form. Dette trin er trivielt. Tensoren har samme dimension som objekterne X_batches og y_batches.

For eksempel er tensoren X en pladsholder (tjek selvstudiet om Introduktion til Tensorflow for at genopfriske dit sind om variabel deklaration) har tre dimensioner:

  • Bemærk: batchens størrelse
  • n_windows: Længde på vinduerne. dvs. antallet af gange, modellen kigger bagud
  • n_input: Antal input

Resultatet er:

tf.placeholder(tf.float32, [None, n_windows, n_input])
## 1. Construct the tensors
X = tf.placeholder(tf.float32, [None, n_windows, n_input])   
y = tf.placeholder(tf.float32, [None, n_windows, n_output])

Trin 3.2) Opret RNN

I den anden del af dette RNN TensorFlow-eksempel skal du definere netværkets arkitektur. Som før bruger du objektet BasicRNNCell og dynamic_rnn fra TensorFlow estimator.

## 2. create the model
basic_cell = tf.contrib.rnn.BasicRNNCell(num_units=r_neuron, activation=tf.nn.relu)   
rnn_output, states = tf.nn.dynamic_rnn(basic_cell, X, dtype=tf.float32)   

Den næste del er en smule vanskeligere, men tillader hurtigere beregning. Du skal transformere kørselsoutputtet til et tæt lag og derefter konvertere det igen for at have samme dimension som inputtet.

stacked_rnn_output = tf.reshape(rnn_output, [-1, r_neuron])          
stacked_outputs = tf.layers.dense(stacked_rnn_output, n_output)       
outputs = tf.reshape(stacked_outputs, [-1, n_windows, n_output])  

Trin 3.3) Skab tabet og optimeringen

Modeloptimeringen afhænger af den opgave, du udfører. I den forrige tutorial vedr CNN, dit mål var at klassificere billeder, i denne RNN-tutorial er målet lidt anderledes. Du bliver bedt om at lave en forudsigelse på en kontinuert variabel sammenlignet med en klasse.

Denne forskel er vigtig, fordi den vil ændre optimeringsproblemet. Optimeringsproblemet for en kontinuert variabel er at minimere den gennemsnitlige kvadratiske fejl. For at konstruere disse metrics i TF kan du bruge:

  • tf.reduce_sum(tf.square(output – y))

Resten af ​​RNN-koden er den samme som før; du bruger en Adam optimizer til at reducere tabet (dvs. MSE):

  • tf.train.AdamOptimizer(learning_rate=learning_rate)
  • optimizer.minimize(tab)

Det er det, du kan pakke alt sammen, og din model er klar til at træne.

tf.reset_default_graph()
r_neuron = 120    

## 1. Construct the tensors
X = tf.placeholder(tf.float32, [None, n_windows, n_input])   
y = tf.placeholder(tf.float32, [None, n_windows, n_output])

## 2. create the model
basic_cell = tf.contrib.rnn.BasicRNNCell(num_units=r_neuron, activation=tf.nn.relu)   
rnn_output, states = tf.nn.dynamic_rnn(basic_cell, X, dtype=tf.float32)              

stacked_rnn_output = tf.reshape(rnn_output, [-1, r_neuron])          
stacked_outputs = tf.layers.dense(stacked_rnn_output, n_output)       
outputs = tf.reshape(stacked_outputs, [-1, n_windows, n_output])   

## 3. Loss + optimization
learning_rate = 0.001  
 
loss = tf.reduce_sum(tf.square(outputs - y))    
optimizer = tf.train.AdamOptimizer(learning_rate=learning_rate)         
training_op = optimizer.minimize(loss)                                          

init = tf.global_variables_initializer() 

Du træner modellen ved at bruge 1500 epoker og udskriver tabet hver 150 iterationer. Når modellen er trænet, evaluerer du modellen på testsættet og opretter et objekt, der indeholder forudsigelserne som vist i nedenstående eksempel på Recurrent Neural Network.

iteration = 1500 

with tf.Session() as sess:
    init.run()
    for iters in range(iteration):
        sess.run(training_op, feed_dict={X: X_batches, y: y_batches})
        if iters % 150 == 0:
            mse = loss.eval(feed_dict={X: X_batches, y: y_batches})
            print(iters, "\tMSE:", mse)
    
    y_pred = sess.run(outputs, feed_dict={X: X_test})
0 	MSE: 502893.34
150 	MSE: 13839.129
300 	MSE: 3964.835
450 	MSE: 2619.885
600 	MSE: 2418.772
750 	MSE: 2110.5923
900 	MSE: 1887.9644
1050 	MSE: 1747.1377
1200 	MSE: 1556.3398
1350 	MSE: 1384.6113

Endelig i denne RNN Deep Learning-tutorial kan du plotte den faktiske værdi af serien med den forudsagte værdi. Hvis din model er rettet, skal de forudsagte værdier sættes oven på de faktiske værdier.

Som du kan se, har modellen plads til forbedringer. Det er op til dig at ændre hyperparametrene som windows, batchstørrelsen af ​​antallet af tilbagevendende neuroner.

plt.title("Forecast vs Actual", fontsize=14)
plt.plot(pd.Series(np.ravel(y_test)), "bo", markersize=8, label="Actual", color='green')
plt.plot(pd.Series(np.ravel(y_pred)), "r.", markersize=8, label="Forecast", color='red')
plt.legend(loc="lower left")
plt.xlabel("Time")

plt.show()
Prognose vs. faktisk

Prognose vs. faktisk

Resumé

Et tilbagevendende neuralt netværk er en robust arkitektur til at håndtere tidsserier eller tekstanalyse. Outputtet fra den tidligere tilstand er feedback for at bevare netværkets hukommelse over tid eller sekvens af ord.

I TensorFlow kan du bruge følgende koder til at træne et TensorFlow Recurrent Neural Network til tidsserier:

Parametre for modellen

n_windows = 20   
n_input =  1
n_output = 1
size_train = 201

Definer modellen

X = tf.placeholder(tf.float32, [None, n_windows, n_input])   
y = tf.placeholder(tf.float32, [None, n_windows, n_output])

basic_cell = tf.contrib.rnn.BasicRNNCell(num_units=r_neuron, activation=tf.nn.relu)   
rnn_output, states = tf.nn.dynamic_rnn(basic_cell, X, dtype=tf.float32)              

stacked_rnn_output = tf.reshape(rnn_output, [-1, r_neuron])          
stacked_outputs = tf.layers.dense(stacked_rnn_output, n_output)       
outputs = tf.reshape(stacked_outputs, [-1, n_windows, n_output])

Konstruer optimeringen

learning_rate = 0.001  
 
loss = tf.reduce_sum(tf.square(outputs - y))    
optimizer = tf.train.AdamOptimizer(learning_rate=learning_rate)         
training_op = optimizer.minimize(loss)                                          

Træn modellen

init = tf.global_variables_initializer() 
iteration = 1500 

with tf.Session() as sess:
    init.run()
    for iters in range(iteration):
        sess.run(training_op, feed_dict={X: X_batches, y: y_batches})
        if iters % 150 == 0:
            mse = loss.eval(feed_dict={X: X_batches, y: y_batches})
            print(iters, "\tMSE:", mse)
    
    y_pred = sess.run(outputs, feed_dict={X: X_test})