Tutorial RNN (rețea neuronală recurentă): Exemplu TensorFlow

De ce avem nevoie de o rețea neuronală recurentă (RNN)?

Rețeaua neuronală recurentă (RNN) vă permite să modelați unități de memorie pentru a persista datele și a modela dependențe pe termen scurt. De asemenea, este utilizat în prognoza serii temporale pentru identificarea corelațiilor și modelelor de date. De asemenea, ajută la producerea de rezultate predictive pentru date secvențiale prin furnizarea unui comportament similar ca un creier uman.

Structura unei rețele neuronale artificiale este relativ simplă și se referă în principal la multiplicarea matricei. În timpul primului pas, intrările sunt înmulțite cu ponderi inițial aleatoare și părtinirea, transformată cu o funcție de activare, iar valorile de ieșire sunt utilizate pentru a face o predicție. Acest pas oferă o idee despre cât de departe este rețeaua de realitate.

Metrica aplicată este pierderea. Cu cât funcția de pierdere este mai mare, cu atât modelul este mai prost. Pentru a îmbunătăți cunoașterea rețelei, este necesară o anumită optimizare prin ajustarea greutăților rețelei. Coborârea gradientului stocastic este metoda folosită pentru a modifica valorile greutăților în direcția dreptului. Odată efectuată ajustarea, rețeaua poate folosi un alt lot de date pentru a-și testa noile cunoștințe.

Eroarea, din fericire, este mai mică decât înainte, dar nu suficient de mică. Pasul de optimizare se face iterativ până când eroarea este minimizată, adică nu mai pot fi extrase informații.

Problema cu acest tip de model este ca nu are memorie. Înseamnă că intrarea și ieșirea sunt independente. Cu alte cuvinte, modelului nu îi pasă de ceea ce a venit înainte. Se ridică o întrebare când trebuie să preziceți serii de timp sau propoziții, deoarece rețeaua trebuie să aibă informații despre datele istorice sau despre cuvintele trecute.

Pentru a depăși această problemă, a fost dezvoltat un nou tip de arhitectură: Rețeaua neuronală recurentă (RNN în continuare)

Ce este o rețea neuronală recurentă (RNN)?

A Rețea neuronală recurentă (RNN) este o clasă de Retele neuronale artificiale în care legătura dintre diferite noduri formează un graf direcționat pentru a da un comportament dinamic temporal. Ajută la modelarea datelor secvențiale care sunt derivate din rețelele feedforward. Funcționează în mod similar creierului uman pentru a oferi rezultate predictive.

O rețea neuronală recurentă arată destul de asemănătoare cu o rețea neuronală tradițională, cu excepția faptului că neuronilor li se adaugă o stare de memorie. Calculul pentru a include o memorie este simplu.

Imaginați-vă un model simplu cu un singur neuron alimentat de un lot de date. Într-o rețea neuronală tradițională, modelul produce rezultatul înmulțind intrarea cu greutatea și funcția de activare. Cu un RNN, această ieșire este trimisă înapoi la sine de câte ori. Noi sunam pas de timp intervalul de timp în care ieșirea devine intrarea următoarei înmulțiri de matrice.

De exemplu, în imaginea de mai jos, puteți vedea că rețeaua este compusă dintr-un neuron. Rețeaua calculează multiplicarea matricelor între intrare și greutate și adaugă neliniaritate cu funcția de activare. Devine ieșirea la t-1. Această ieșire este intrarea celei de-a doua înmulțiri a matricei.

Rețea neuronală recurentă (RNN)
Rețea neuronală recurentă (RNN)

Mai jos, codificăm un RNN simplu în TensorFlow pentru a înțelege pasul și, de asemenea, forma ieșirii.

Rețeaua este compusă din:

  • Patru intrări
  • Șase neuroni
  • 2 pași de timp

Rețeaua va proceda așa cum este prezentat în imaginea de mai jos.

Rețea neuronală recurentă (RNN)

Rețeaua se numește „recurent” deoarece efectuează aceeași operație în fiecare pătrat de activare. Rețeaua a calculat greutățile intrărilor și ale ieșirii anterioare înainte de a utiliza o funcție de activare.

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
    ])

Putem construi rețeaua cu un substituent pentru date, etapa recurentă și rezultatul.

  1. Definiți substituentul pentru date
X = tf.placeholder(tf.float32, [None, n_timesteps, n_inputs])

Aici:

  • Niciunul: necunoscut și va lua dimensiunea lotului
  • n_timesteps: De câte ori rețeaua va trimite ieșirea înapoi la neuron
  • n_inputs: Numărul de intrări per lot
  1. Definiți rețeaua recurentă

După cum se menționează în imaginea de mai sus, rețeaua este compusă din 6 neuroni. Rețeaua va calcula un produs punctual:

  • Date de intrare cu primul set de greutăți (adică 6: egal cu numărul de neuroni)
  • Ieșire anterioară cu un al doilea set de greutăți (adică 6: corespunzător numărului de ieșiri)

Rețineți că, în timpul primului feedforward, valorile rezultatelor anterioare sunt egale cu zerouri, deoarece nu avem nicio valoare disponibilă.

Obiectul pentru a construi un RNN este tf.contrib.rnn.BasicRNNCell cu argumentul num_units pentru a defini numărul de intrare

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

Acum că rețeaua este definită, puteți calcula ieșirile și stările

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

Acest obiect folosește o buclă internă pentru a multiplica matricele de numărul corespunzător de ori.

Rețineți că neuronul recurent este o funcție a tuturor intrărilor pașilor de timp anteriori. Acesta este modul în care rețeaua își construiește propria memorie. Informațiile din timpul precedent se pot propaga în viitor. Aceasta este magia rețelei neuronale recurente

## 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]]

În scop explicativ, imprimați valorile stării anterioare. Ieșirea tipărită mai sus arată rezultatul din ultima stare. Acum tipăriți toate rezultatele, puteți observa că stările sunt ieșirea anterioară a fiecărui lot. Adică, ieșirea anterioară conține informații despre întreaga secvență.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)

Rețea neuronală recurentă (RNN)

Ieșirea are forma (3, 2, 6):

  • 3: Numărul de loturi
  • 2: Numărul pasului de timp
  • 6: Numărul de neuroni

Optimizarea unei rețele neuronale recurente este identică cu o rețea neuronală tradițională. Veți vedea mai detaliat cum să codificați optimizarea în următoarea parte a acestui tutorial de rețea neuronală recurentă.

Aplicații ale RNN

RNN are multiple utilizări, mai ales când vine vorba de prezicerea viitorului. În industria financiară, RNN poate fi de ajutor în prezicerea prețurilor acțiunilor sau a semnului direcției pieței de valori (adică pozitiv sau negativ).

RNN este util pentru o mașină autonomă, deoarece poate evita un accident de mașină anticipând traiectoria vehiculului.

RNN este utilizat pe scară largă în analiza textului, subtitrărea imaginilor, analiza sentimentelor și traducerea automată. De exemplu, se poate folosi o recenzie a filmului pentru a înțelege sentimentul pe care l-a perceput spectatorul după vizionarea filmului. Automatizarea acestei sarcini este foarte utilă atunci când compania de film nu are suficient timp pentru a revizui, eticheta, consolida și analiza recenziile. Aparatul poate face treaba cu un nivel mai ridicat de precizie.

Limitările RNN

În teorie, RNN ar trebui să transporte informațiile până la ori. Cu toate acestea, este destul de dificil să propagați toate aceste informații atunci când intervalul de timp este prea lung. Când o rețea are prea multe straturi adânci, devine imposibil de antrenat. Această problemă se numește: dispariția problemei gradientului. Dacă vă amintiți, rețeaua neuronală actualizează greutatea folosind algoritmul de coborâre a gradientului. Gradienții devin mai mici atunci când rețeaua progresează în straturi inferioare.

În concluzie, gradienții rămân constante, ceea ce înseamnă că nu există spațiu de îmbunătățire. Modelul învață dintr-o modificare a gradientului; această modificare afectează ieșirea rețelei. Cu toate acestea, dacă diferența de gradient este prea mică (adică greutățile se schimbă puțin), rețeaua nu poate învăța nimic și deci ieșirea. Prin urmare, o rețea care se confruntă cu o problemă de gradient care dispare nu poate converge către o soluție bună.

Îmbunătățirea LSTM

Pentru a depăși problema potențială a gradientului de dispariție cu care se confruntă RNN, trei cercetători, Hochreiter, Schmidhuber și Bengio, au îmbunătățit RNN cu o arhitectură numită Long Short-Term Memory (LSTM). Pe scurt, LSMT furnizează rețelei informații din trecut relevante pentru vremuri mai recente. Aparatul folosește o arhitectură mai bună pentru a selecta și a transporta informațiile înapoi în timp ulterioară.

Arhitectura LSTM este disponibilă în TensorFlow, tf.contrib.rnn.LSTMCell. LSTM este în afara domeniului de aplicare al tutorialului. Vă puteți adresa oficialului documentaţie pentru mai multe informații

RNN în serii de timp

În acest tutorial TensorFlow RNN, veți folosi un RNN cu date din seria temporală. Seriile temporale depind de timpul precedent, ceea ce înseamnă că valorile trecute includ informații relevante din care poate învăța rețeaua. Ideea din spatele predicției serii de timp este de a estima valoarea viitoare a unei serii, să spunem, prețul acțiunilor, temperatura, PIB-ul și așa mai departe.

Pregătirea datelor pentru Keras RNN și seriile de timp poate fi puțin dificilă. În primul rând, obiectivul este de a prezice următoarea valoare a seriei, adică veți folosi informațiile trecute pentru a estima valoarea la t + 1. Eticheta este egală cu secvența de intrare și este deplasată cu o perioadă înainte. În al doilea rând, numărul de intrări este setat la 1, adică o observație pe dată. În cele din urmă, pasul de timp este egal cu succesiunea valorii numerice. De exemplu, dacă setați intervalul de timp la 10, secvența de intrare va reveni de zece ori consecutiv.

Uită-te la graficul de mai jos, am reprezentat datele seriei temporale în stânga și o secvență de intrare fictivă în dreapta. Creați o funcție pentru a returna un set de date cu valoare aleatorie pentru fiecare zi din ianuarie 2001 până în decembrie 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)

producție

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 în seria temporală

Partea din dreapta a graficului arată toate seriile. A început din 2001 și se termină în 2019. Nu are sens să alimentați toate datele din rețea, în schimb, trebuie să creați un lot de date cu o lungime egală cu pasul de timp. Acest lot va fi variabila X. Variabila Y este aceeași cu X, dar deplasată cu o perioadă (adică doriți să prognozați t+1).

Ambii vectori au aceeași lungime. O puteți vedea în partea dreaptă a graficului de mai sus. Linia reprezintă cele zece valori ale intrării X, în timp ce punctele roșii sunt cele zece valori ale etichetei, Y. Rețineți că, eticheta începe cu o perioadă înainte de X și se termină cu o perioadă după.

Creați un RNN pentru a prezice serii temporale în TensorFlow

Acum, în acest antrenament RNN, este timpul să vă construiți primul RNN pentru a prezice seria de mai sus. Trebuie să specificați niște hiperparametri (parametrii modelului, adică numărul de neuroni etc.) pentru model:

  • Număr de intrări: 1
  • Pas de timp (ferestre în seria temporală): 10
  • Număr de neuroni: 120
  • Număr de ieșiri: 1

Rețeaua ta va învăța dintr-o secvență de 10 zile și va conține 120 de neuroni recurenți. Alimentați modelul cu o singură intrare, adică o zi. Simțiți-vă liber să modificați valorile pentru a vedea dacă modelul s-a îmbunătățit.

Înainte de a construi modelul, trebuie să împărțiți setul de date într-un set de trenuri și un set de testare. Setul de date complet are 222 de puncte de date; veți folosi primele 201 de puncte pentru a antrena modelul și ultimele 21 de puncte pentru a vă testa modelul.

După ce definiți un tren și un set de testare, trebuie să creați un obiect care conține loturile. În aceste loturi, aveți valori X și valori Y. Amintiți-vă că valorile X sunt cu o perioadă întârziată. Prin urmare, utilizați primele 200 de observații și pasul de timp este egal cu 10. Obiectul X_batches ar trebui să conțină 20 de loturi de dimensiunea 10*1. Y_batches are aceeași formă ca obiectul X_batches, dar cu o perioadă înainte.

Pas 1) Creați trenul și testați

În primul rând, transformi seria într-un NumPy matrice; apoi definiți ferestrele (de exemplu, numărul de timp din care rețeaua va învăța), numărul de intrare, ieșire și dimensiunea setului de tren, așa cum se arată în exemplul TensorFlow RNN de mai jos.

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

După aceea, pur și simplu împărțiți matricea în două seturi de date.

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

Pas 2) Creați funcția pentru a returna X_batches și y_batches

Pentru a fi mai ușor, puteți crea o funcție care returnează două matrice diferite, una pentru X_batches și una pentru y_batches.

Să scriem o funcție RNN TensorFlow pentru a construi loturile.

Rețineți că, loturile X sunt întârziate cu o perioadă (luăm valoarea t-1). Ieșirea funcției ar trebui să aibă trei dimensiuni. Primele dimensiuni sunt egale cu numărul de loturi, a doua dimensiunea ferestrelor și ultima cu numărul de intrări.

Partea dificilă este să selectați corect punctele de date. Pentru punctele de date X, alegeți observațiile de la t = 1 la t = 200, în timp ce pentru punctul de date Y, returnați observațiile de la t = 2 la 201. Odată ce aveți punctele de date corecte, este ușor să remodelați serialul.

Pentru a construi obiectul cu loturile, trebuie să împărțiți setul de date în zece loturi de lungime egală (adică 20). Puteți folosi metoda de remodelare și treceți -1, astfel încât seria să fie similară cu dimensiunea lotului. Valoarea 20 este numărul de observații pe lot și 1 este numărul de intrare.

Trebuie să faceți același pas, dar pentru etichetă.

Rețineți că, trebuie să mutați datele la numărul de ori pe care doriți să le prognozați. De exemplu, dacă doriți să estimați un timp înainte, atunci schimbați seria cu 1. Dacă doriți să prognozați două zile, atunci mutați datele cu 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

Acum că funcția este definită, o puteți apela pentru a crea loturile așa cum se arată în exemplul RNN de mai jos.

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

Puteți imprima forma pentru a vă asigura că dimensiunile sunt corecte.

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

Trebuie să creați setul de testare cu un singur lot de date și 20 de observații.

Rețineți că, estimați zile după zile, înseamnă că a doua valoare estimată se va baza pe valoarea reală a primei zile (t+1) a setului de date de testare. De fapt, adevărata valoare va fi cunoscută.

Dacă doriți să prognozați t+2 (adică, cu două zile înainte), trebuie să utilizați valoarea prezisă t+1; dacă urmează să preziceți t+3 (cu trei zile înainte), trebuie să utilizați valoarea prezisă t+1 și t+2. Este logic că este dificil să prezici cu exactitate t+n zile înainte.

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)

Bine, dimensiunea lotului este gata, puteți construi arhitectura RNN. Amintiți-vă, aveți 120 de neuroni recurenți.

Pas 3) Construiți modelul

Pentru a crea modelul, trebuie să definiți trei părți:

  1. Variabila cu tensorii
  2. RNN
  3. Pierderea și optimizarea

Pas 3.1) Variabile

Trebuie să specificați variabilele X și y cu forma corespunzătoare. Acest pas este banal. Tensorul are aceeași dimensiune ca și obiectele X_batch și y_batch.

De exemplu, tensorul X este un substituent (consultați tutorialul despre Introducere în flux tensor pentru a vă reîmprospăta mintea cu privire la declarația variabilă) are trei dimensiuni:

  • Notă: dimensiunea lotului
  • n_windows: Lungimea ferestrelor. adică numărul de timp în care modelul se uită înapoi
  • n_input: Numărul de intrare

Rezultatul este:

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])

Pas 3.2) Creați RNN

În a doua parte a acestui exemplu RNN TensorFlow, trebuie să definiți arhitectura rețelei. Ca și înainte, utilizați obiectul BasicRNNCell și dynamic_rnn din estimatorul TensorFlow.

## 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)   

Următoarea parte este puțin mai complicată, dar permite un calcul mai rapid. Trebuie să transformați rezultatul rulării într-un strat dens și apoi să îl convertiți din nou pentru a avea aceeași dimensiune ca și intrarea.

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])  

Pas 3.3) Creați pierderea și optimizarea

Optimizarea modelului depinde de sarcina pe care o efectuați. În tutorialul anterior pe CNN, obiectivul tău a fost să clasificăm imaginile, în acest tutorial RNN, obiectivul este ușor diferit. Vi se cere să faceți o predicție asupra unei variabile continue în comparație cu o clasă.

Această diferență este importantă deoarece va schimba problema de optimizare. Problema de optimizare pentru o variabilă continuă este de a minimiza eroarea pătratică medie. Pentru a construi aceste valori în TF, puteți utiliza:

  • tf.reduce_sum(tf.square(ieșiri – y))

Restul codului RNN este același ca înainte; utilizați un optimizator Adam pentru a reduce pierderea (adică, MSE):

  • tf.train.AdamOptimizer(learning_rate=learning_rate)
  • optimizator.minimize(pierdere)

Gata, poți împacheta totul, iar modelul tău este gata de antrenament.

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() 

Veți antrena modelul folosind 1500 de epoci și veți imprima pierderea la fiecare 150 de iterații. Odată ce modelul este antrenat, evaluați modelul pe setul de testare și creați un obiect care conține predicțiile, așa cum se arată în exemplul de mai jos al rețelei neuronale recurente.

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

În cele din urmă, în acest tutorial RNN Deep Learning, puteți reprezenta grafic valoarea reală a seriei cu valoarea prezisă. Dacă modelul dvs. este corectat, valorile prezise ar trebui puse peste valorile reale.

După cum puteți vedea, modelul are loc de îmbunătățire. Depinde de dvs. să modificați hiperparametrii precum ferestrele, dimensiunea lotului a numărului de neuroni recurenți.

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()
Prognoză vs Real

Prognoză vs Real

Rezumat

O rețea neuronală recurentă este o arhitectură robustă pentru a face față seriilor de timp sau analizei de text. Ieșirea stării anterioare este feedback pentru a păstra memoria rețelei în timp sau secvența de cuvinte.

În TensorFlow, puteți folosi următoarele coduri pentru a antrena o rețea neuronală recurentă TensorFlow pentru serii cronologice:

Parametrii modelului

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

Definiți modelul

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])

Construiți optimizarea

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)                                          

Antrenează modelul

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})