„TensorFlow Autoencoder“: duomenų rinkinys su gilaus mokymosi pavyzdžiu

Turinys:

Anonim

Kas yra automatinis koderis?

Autoencoder“ yra priemonė efektyviai, neprižiūrimai išmokti duomenų kodavimo. Tai yra dirbtinio neuroninio tinklo rūšis, padedanti išmokti vaizduoti duomenų rinkinius, norint sumažinti matmenis, mokant neuroninį tinklą ignoruoti signalo triukšmą. Tai puiki priemonė atkuriant įvestį.

Paprastais žodžiais tariant, mašina daro, tarkime, vaizdą ir gali sukurti glaudžiai susijusią nuotrauką. Tokio neuroninio tinklo įvestis nėra paženklinta, o tai reiškia, kad tinklas gali mokytis be priežiūros. Tiksliau, įvestis yra užkoduota tinklo, kad būtų galima sutelkti dėmesį tik į svarbiausią funkciją. Tai yra viena iš priežasčių, kodėl automatinis koderis yra populiarus mažinant matmenis. Be to, kuriant generatyvius mokymosi modelius galima naudoti automatinius kodavimo įrenginius . Pavyzdžiui, nervų tinklą galima treniruoti naudojant veidų rinkinį ir tada sukurti naujus veidus.

Šioje „TensorFlow Autoencoder“ pamokoje sužinosite:

  • Kas yra automatinis koderis?
  • Kaip veikia „Autoencoder“?
  • „Stacked Autoencoder“ pavyzdys
  • Sukurkite „Autoencoder“ su „TensorFlow“
  • Išankstinis vaizdo apdorojimas
  • Nustatykite duomenų rinkinio įvertiklį
  • Sukurkite tinklą

Kaip veikia „Autoencoder“?

Automatinio kodavimo įrenginio paskirtis yra nustatyti įvesties apytikslę vertę, sutelkiant dėmesį tik į pagrindines savybes. Galite pagalvoti, kodėl ne tik sužinojus, kaip nukopijuoti ir įklijuoti įvestį, kad būtų sukurta išvestis. Tiesą sakant, automatinis koderis yra visuma apribojimų, verčiančių tinklą išmokti naujų būdų pateikti duomenis, kurie skiriasi nuo vien tik išvesties kopijavimo.

Tipinis automatinis koderis apibrėžiamas su įėjimu, vidiniu atvaizdavimu ir išvestimi (įvesties apytikslė reikšmė). Mokymasis vyksta sluoksniuose, pritvirtintuose prie vidinės reprezentacijos. Iš tikrųjų yra du pagrindiniai sluoksnių blokai, kurie atrodo kaip tradicinis neuronų tinklas. Nedidelis skirtumas yra tas, kad sluoksnis, kuriame yra išvestis, turi būti lygus įėjimui. Žemiau esančiame paveikslėlyje pradinė įvestis patenka į pirmąjį bloką, vadinamą koduotoju . Šis vidinis atvaizdavimas suglaudina (sumažina) įvesties dydį. Antrame bloke įvyksta įvesties rekonstrukcija. Tai yra dekodavimo etapas.

„Autoencoder“ darbas

Modelis atnaujins svorį, sumažindamas nuostolių funkciją. Modelis baudžiamas, jei rekonstrukcijos rezultatas skiriasi nuo įvesties.

Konkrečiai įsivaizduokite 50x50 dydžio (ty 250 pikselių) paveikslėlį ir neuronų tinklą, kuriame yra tik vienas paslėptas sluoksnis, sudarytas iš šimto neuronų. Mokymasis atliekamas funkcijų žemėlapyje, kuris yra du kartus mažesnis už įvestį. Tai reiškia, kad tinklas turi rasti būdą rekonstruoti 250 taškų, kai tik neuronų vektorius yra lygus 100.

„Stacked Autoencoder“ pavyzdys

Šioje „Autoencoder“ mokymo programoje sužinosite, kaip naudoti sukrautą automatinį kodavimo įrenginį. Architektūra yra panaši į tradicinį neuronų tinklą. Įėjimas eina į paslėptą sluoksnį, kad būtų suspaustas arba sumažintas jo dydis, ir tada pasiekia rekonstrukcijos sluoksnius. Tikslas yra sukurti tokį pat išvesties vaizdą kaip originalas. Modelis turi išmokti būdą, kaip pasiekti savo užduotį taikant apribojimų rinkinį, ty su mažesniu aspektu.

Šiais laikais „Autoencoders“ programoje „Deep Learning“ dažniausiai naudojami paveikslėliai. Įsivaizduokite vaizdą su įbrėžimais; žmogus vis dar sugeba atpažinti turinį. Automatinio kodavimo įrenginio išjungimo idėja yra pridėti triukšmo prie nuotraukos, kad priverstų tinklą išmokti duomenų šabloną.

Kita naudinga „Autoencoder Deep Learning“ šeima yra variacinis automatas. Šio tipo tinklai gali generuoti naujus vaizdus. Įsivaizduokite, kad mokote tinklą su vyro atvaizdu; toks tinklas gali sukurti naujus veidus.

Sukurkite „Autoencoder“ su „TensorFlow“

Šioje pamokoje sužinosite, kaip sukurti sukrautą automatą, kad atkurtumėte vaizdą.

Naudosite CIFAR-10 duomenų rinkinį, kuriame yra 60000 spalvotų 32x32 vaizdų. „Autoencoder“ duomenų rinkinys jau padalytas iš 50000 vaizdų, skirtų mokymui, ir 10000, kad būtų galima išbandyti. Yra iki dešimties klasių:

  • Lėktuvas
  • Automobilis
  • Paukštis
  • Katė
  • Elniai
  • Šuo
  • Varlė
  • Arklys
  • Laivas
  • Sunkvežimis

Vaizdus iš šio URL turite atsisiųsti https://www.cs.toronto.edu/~kriz/cifar.html ir išpakuoti. Kataloge „10 partijų-py“ yra penkios duomenų partijos su 10000 vaizdų, kurių kiekviena atsitiktine tvarka.

Prieš kurdami ir mokydami modelį, turite pritaikyti tam tikrą duomenų apdorojimą. Jūs elgsitės taip:

  1. Importuokite duomenis
  2. Konvertuokite duomenis į nespalvotą formatą
  3. Pridėkite visas partijas
  4. Sukurkite mokymo duomenų rinkinį
  5. Sukurkite vaizdo vizualizatorių

Išankstinis vaizdo apdorojimas

1 žingsnis) Importuokite duomenis.

Remiantis oficialia svetaine, duomenis galite įkelti naudodami šį kodą. „Autoencoder“ kodas įkelia duomenis į žodyną su duomenimis ir etikete . Atkreipkite dėmesį, kad kodas yra funkcija.

import numpy as npimport tensorflow as tfimport pickledef unpickle(file):import picklewith open(file, 'rb') as fo:dict = pickle.load(fo, encoding='latin1')return dict

2 žingsnis) Konvertuokite duomenis į nespalvotą formatą

Kad būtų paprasčiau, duomenis paversite pilka spalva. Tai reiškia, kad spalvų vaizdui tik vienas matmuo prieš tris. Dauguma neuroninio tinklo veikia tik su vienu matmenų įėjimu.

def grayscale(im):return im.reshape(im.shape[0], 3, 32, 32).mean(1).reshape(im.shape[0], -1)

3 žingsnis) Pridėkite visas partijas

Dabar, kai abi funkcijos yra sukurtos ir duomenų rinkinys įkeltas, galite parašyti kilpą, kad pridėtumėte duomenis atmintyje. Jei atidžiai patikrinsite, išpakuotas failas su duomenimis bus pavadintas data_batch_ su skaičiumi nuo 1 iki 5. Galite perjungti failus ir pridėti prie duomenų.

Atlikę šį veiksmą, spalvų duomenis paversite pilkos skalės formatu. Kaip matote, duomenų forma yra 50000 ir 1024. Dabar 32 * 32 pikseliai yra išlyginti iki 2014 m.

# Load the data into memorydata, labels = [], []## Loop over the bfor i in range(1, 6):filename = './cifar-10-batches-py/data_batch_' + str(i)open_data = unpickle(filename)if len(data)> 0:data = np.vstack((data, open_data['data']))labels = np.hstack((labels, open_data['labels']))else:data = open_data['data']labels = open_data['labels']data = grayscale(data)x = np.matrix(data)y = np.array(labels)print(x.shape)(50000, 1024)

Pastaba: Pakeiskite „./cifar-10-batches-py/data_batch_“ į faktinę failo vietą. Pavyzdžiui, „Windows“ mašinoje kelias gali būti failo pavadinimas = 'E: \ cifar-10-batches-py \ data_batch_' + str (i)

4 žingsnis) Sukurkite mokymo duomenų rinkinį

Kad treniruotė būtų greitesnė ir lengvesnė, treniruosite modelį tik ant žirgo atvaizdų. Žirgai yra septintoji etiketės duomenų klasė. Kaip minėta CIFAR-10 duomenų rinkinio dokumentuose, kiekvienoje klasėje yra 5000 vaizdų. Galite atsispausdinti duomenų formą, kad patvirtintumėte, jog yra 5 000 vaizdų su 1024 stulpeliais, kaip parodyta toliau pateiktame „TensorFlow Autoencoder“ pavyzdžio žingsnyje.

horse_i = np.where(y == 7)[0]horse_x = x[horse_i]print(np.shape(horse_x))(5000, 1024)

5 žingsnis) Sukurkite vaizdo vizualizatorių

Galiausiai sukonstruojate funkciją vaizdams braižyti. Jums reikės šios funkcijos norint atspausdinti rekonstruotą vaizdą iš automatinio kodavimo įrenginio.

Paprastas vaizdų spausdinimo būdas yra naudoti objektą „imshow“ iš „matplotlib“ bibliotekos. Atkreipkite dėmesį, kad turite konvertuoti duomenų formą iš 1024 į 32 * 32 (ty vaizdo formatą).

# To plot pretty figures%matplotlib inlineimport matplotlibimport matplotlib.pyplot as pltdef plot_image(image, shape=[32, 32], cmap = "Greys_r"):plt.imshow(image.reshape(shape), cmap=cmap,interpolation="nearest")plt.axis("off")

Funkcijoje yra 3 argumentai:

  • Vaizdas: įvestis
  • Forma: sąrašas, vaizdo matmuo
  • Cmap: pasirinkite spalvų žemėlapį. Pagal numatytuosius nustatymus pilka

Galite pabandyti pateikti pirmąjį duomenų rinkinio vaizdą. Turėtumėte pamatyti žmogų ant žirgo.

plot_image(horse_x[1], shape=[32, 32], cmap = "Greys_r") 

Nustatykite duomenų rinkinio įvertiklį

Gerai, dabar, kai duomenų rinkinys yra paruoštas naudoti, galite pradėti naudoti „Tensorflow“. Prieš kurdami modelį, tinklui tiekti naudokime „Tensorflow“ duomenų rinkinio įvertiklį.

Sukursite duomenų rinkinį naudodami „TensorFlow“ įvertiklį. Norėdami atnaujinti savo mintis, turite naudoti:

  • from_tensor_slices
  • pakartoti
  • partija

Visas duomenų rinkinio sukūrimo kodas yra:

dataset = tf.data.Dataset.from_tensor_slices(x).repeat().batch(batch_size) 

Atminkite, kad x yra tokios formos vietos rezervavimo ženklas:

  • [None, n_inputs]: nustatykite į None, nes vaizdo tiekimo į tinklą skaičius yra lygus paketo dydžiui.

Išsamesnės informacijos ieškokite tiesinės regresijos pamokoje.

Po to turite sukurti iteratorių. Be šios kodo eilutės jokie duomenys nebus perduodami.

iter = dataset.make_initializable_iterator() # create the iteratorfeatures = iter.get_next() 

Dabar, kai dujotiekis yra paruoštas, galite patikrinti, ar pirmasis vaizdas yra toks pats kaip anksčiau (ty žmogus ant žirgo).

Jūs nustatote paketo dydį į 1, nes norite rinkti duomenų rinkinį tik su vienu vaizdu. Duomenų matmenis galite pamatyti spausdindami (sess.run (features) .shape). Jis lygus (1, 1024). 1 reiškia, kad tiekiamas tik vienas vaizdas su 1024. Jei nustatomas dviejų partijų dydis, du vamzdžiai eis per du vaizdus. (Nekeiskite paketo dydžio. Priešingu atveju tai sukels klaidą. Tik vienas vaizdas vienu metu gali pereiti į funkciją plot_image ().

## Parametersn_inputs = 32 * 32BATCH_SIZE = 1batch_size = tf.placeholder(tf.int64)# using a placeholderx = tf.placeholder(tf.float32, shape=[None,n_inputs])## Datasetdataset = tf.data.Dataset.from_tensor_slices(x).repeat().batch(batch_size)iter = dataset.make_initializable_iterator() # create the iteratorfeatures = iter.get_next()## Print the imagewith tf.Session() as sess:# feed the placeholder with datasess.run(iter.initializer, feed_dict={x: horse_x,batch_size: BATCH_SIZE})print(sess.run(features).shape)plot_image(sess.run(features), shape=[32, 32], cmap = "Greys_r")(1, 1024)

Sukurkite tinklą

Atėjo laikas sukurti tinklą. Jūs mokysite sukrautą automatinį kodavimo įrenginį, tai yra tinklą su keliais paslėptais sluoksniais.

Jūsų tinkle bus vienas įvesties sluoksnis su 1024 taškais, ty 32x32, vaizdo forma.

Kodavimo bloke bus vienas viršutinis paslėptas sluoksnis su 300 neuronų, centrinis - 150 neuronų. Dekoderio blokas yra simetriškas koduotojui. Toliau pateiktame paveikslėlyje galite vizualizuoti tinklą. Atminkite, kad galite pakeisti paslėptų ir centrinių sluoksnių reikšmes.

„Autoencoder“ tinklo kūrimas

Autokoderio kūrimas yra labai panašus į bet kurį kitą giluminio mokymosi modelį.

Modelį sukursite atlikdami šiuos veiksmus:

  1. Apibrėžkite parametrus
  2. Apibrėžkite sluoksnius
  3. Apibrėžkite architektūrą
  4. Apibrėžkite optimizavimą
  5. Paleiskite modelį
  6. Įvertinkite modelį

Ankstesniame skyriuje sužinojote, kaip sukurti vamzdyną modeliui tiekti, todėl nereikia dar kartą kurti duomenų rinkinio. Sukursite keturių sluoksnių automatinį kodavimo įrenginį. Jūs naudojate „Xavier“ inicializavimą. Tai yra būdas nustatyti pradinius svorius, lygius tiek įvesties, tiek išvesties dispersijai. Galiausiai naudojate elu aktyvinimo funkciją. Nuostolių funkciją sureguliuoji naudodamas L2 reguliatorių.

1 žingsnis. Apibrėžkite parametrus

Pirmasis žingsnis reiškia apibrėžti neuronų skaičių kiekviename sluoksnyje, mokymosi greitį ir reguliatoriaus hiperparametrą.

Prieš tai funkciją importuojate iš dalies. Tai yra geresnis būdas apibrėžti tankių sluoksnių parametrus. Žemiau pateiktas kodas apibrėžia automatinio koderio architektūros vertes. Kaip jau buvo minėta anksčiau, autokoderis turi du sluoksnius, pirmuosiuose sluoksniuose yra 300 neuronų, antruosiuose - 150 neuronų. Jų vertės saugomos aplankuose n_hidden_1 ir n_hidden_2.

Turite apibrėžti mokymosi greitį ir L2 hiperparametrą. Reikšmės saugomos mokymosi_rate ir l2_reg

from functools import partial## Encodern_hidden_1 = 300n_hidden_2 = 150 # codings## Decodern_hidden_3 = n_hidden_1n_outputs = n_inputslearning_rate = 0.01l2_reg = 0.0001

„Xavier“ inicializavimo technika iškviečiama objektu „xavier_initializer“ iš įvertintojo indėlio. Tame pačiame įvertinime galite pridėti reguliatorių naudodami „l2_ regularizer“

## Define the Xavier initializationxav_init = tf.contrib.layers.xavier_initializer()## Define the L2 regularizerl2_regularizer = tf.contrib.layers.l2_regularizer(l2_reg)

2 žingsnis. Apibrėžkite sluoksnius

Nustatyti visi tankių sluoksnių parametrai; galite supakuoti viską į kintamąjį dense_layer naudodami objektą dalinis. dense_layer, kuris naudoja ELU aktyvavimą, Xavier inicijavimą ir L2 reguliavimą.

## Create the dense layerdense_layer = partial(tf.layers.dense,activation=tf.nn.elu,kernel_initializer=xav_init,kernel_regularizer=l2_regularizer)

3 žingsnis. Apibrėžkite architektūrą

Pažvelgę ​​į architektūros vaizdą, pastebite, kad tinklas sukrauna tris sluoksnius su išvesties sluoksniu. Žemiau esančiame kode sujungiate atitinkamus sluoksnius. Pavyzdžiui, pirmasis sluoksnis apskaičiuoja taškinį sandaugą tarp įvesties matricos ypatybių ir matricų, kuriose yra 300 svorių. Apskaičiavus taškinį produktą, išėjimas pereina į „Elu“ aktyvavimo funkciją. Išvestis tampa kito sluoksnio įvestimi, todėl ją naudojate apskaičiuodami hidden_2 ir pan. Matricų daugyba kiekvienam sluoksniui yra vienoda, nes naudojate tą pačią aktyvinimo funkciją. Atminkite, kad paskutiniame sluoksnyje, išėjimuose, netaikoma aktyvinimo funkcija. Tai prasminga, nes tai yra rekonstruota įvestis

## Make the mat mulhidden_1 = dense_layer(features, n_hidden_1)hidden_2 = dense_layer(hidden_1, n_hidden_2)hidden_3 = dense_layer(hidden_2, n_hidden_3)outputs = dense_layer(hidden_3, n_outputs, activation=None)

4 žingsnis. Apibrėžkite optimizavimą

Paskutinis žingsnis yra optimizatoriaus sukūrimas. Vidutinio kvadrato klaidą naudojate kaip nuostolių funkciją. Jei prisiminsite linijinės regresijos pamoką, žinote, kad MSE apskaičiuojama pagal skirtumą tarp numatomos išvesties ir tikros etiketės. Čia etiketė yra funkcija, nes modelis bando rekonstruoti įvestį. Todėl norite gauti kvadrato tarp numatomos išvesties ir įvesties skirtumo sumos vidurkį. Naudodami „TensorFlow“, nuostolių funkciją galite užkoduoti taip:

loss = tf.reduce_mean(tf.square(outputs - features)) 

Tada turite optimizuoti nuostolių funkciją. Norėdami apskaičiuoti gradientus, naudokite „Adamo“ optimizavimo priemonę. Tikslo funkcija yra sumažinti nuostolius.

## Optimizeloss = tf.reduce_mean(tf.square(outputs - features))optimizer = tf.train.AdamOptimizer(learning_rate)train = optimizer.minimize(loss)

Dar vienas nustatymas prieš treniruojant modelį. Norite naudoti 150 paketo dydį, ty tiekti vamzdyną po 150 vaizdų kiekvienoje kartojime. Pakartojimų skaičių turite apskaičiuoti rankiniu būdu. Tai trivialu padaryti:

Jei norite kiekvieną kartą perduoti 150 vaizdų ir žinote, kad duomenų rinkinyje yra 5000 vaizdų, kartojimų skaičius yra lygus. „Python“ galite paleisti šiuos kodus ir įsitikinti, kad išvestis yra 33:

BATCH_SIZE = 150### Number of batches : length dataset / batch sizen_batches = horse_x.shape[0] // BATCH_SIZEprint(n_batches)33

5 žingsnis) Paleiskite modelį

Paskutinis, bet ne mažiau svarbus dalykas - mokykite modelį. Jūs mokote modelį su 100 epochų. Tai reiškia, kad modelis 100 kartų matys vaizdus iki optimizuoto svorio.

Jūs jau esate susipažinę su kodais, kad mokytumėte modelį „Tensorflow“. Nedidelis skirtumas yra perduoti duomenis prieš pradedant mokymą. Tokiu būdu modelis treniruojasi greičiau.

Jus domina atspausdinti nuostolius po dešimties epochų, kad sužinotumėte, ar modelis ko nors mokosi (ty nuostoliai mažėja). Mokymai trunka nuo 2 iki 5 minučių, priklausomai nuo jūsų kompiuterio įrangos.

## Set paramsn_epochs = 100## Call Saver to save the model and re-use it later during evaluationsaver = tf.train.Saver()with tf.Session() as sess:sess.run(tf.global_variables_initializer())# initialise iterator with train datasess.run(iter.initializer, feed_dict={x: horse_x,batch_size: BATCH_SIZE})print('Training… ')print(sess.run(features).shape)for epoch in range(n_epochs):for iteration in range(n_batches):sess.run(train)if epoch % 10 == 0:loss_train = loss.eval() # not shownprint("\r{}".format(epoch), "Train MSE:", loss_train)#saver.save(sess, "./my_model_all_layers.ckpt")save_path = saver.save(sess, "./model.ckpt")print("Model saved in path: %s" % save_path)Training… (150, 1024)0 Train MSE: 2934.45510 Train MSE: 1672.67620 Train MSE: 1514.70930 Train MSE: 1404.311840 Train MSE: 1425.05850 Train MSE: 1479.063160 Train MSE: 1609.525970 Train MSE: 1482.322380 Train MSE: 1445.703590 Train MSE: 1453.8597Model saved in path: ./model.ckpt

6 žingsnis) Įvertinkite modelį

Dabar, kai mokote savo modelį, atėjo laikas jį įvertinti. Turite importuoti bandomąjį failą iš failo / cifar-10-batches-py /.

test_data = unpickle('./cifar-10-batches-py/test_batch')test_x = grayscale(test_data['data'])#test_labels = np.array(test_data['labels'])

PASTABA: „Windows“ kompiuteryje kodas tampa test_data = unpickle (r "E: \ cifar-10-batches-py \ test_batch")

Galite pabandyti atspausdinti 13 atvaizdus, ​​tai yra arklys

plot_image(test_x[13], shape=[32, 32], cmap = "Greys_r") 

Norėdami įvertinti modelį, naudosite šio vaizdo pikselių vertę ir pamatysite, ar sugavęs 1024 pikselius koduotojas gali atkurti tą patį vaizdą. Atkreipkite dėmesį, kad jūs nustatote funkciją, skirtą įvertinti modelį su skirtingomis nuotraukomis. Modelis turėtų geriau veikti tik ant arklių.

Funkcijoje yra du argumentai:

  • df: importuokite bandymo duomenis
  • image_number: nurodykite, kokį vaizdą importuoti

Funkcija yra padalinta į tris dalis:

  1. Formuokite vaizdą iki tinkamo matmens, ty 1, 1024
  2. Paduokite modelį nematytu vaizdu, užkoduokite / dekoduokite vaizdą
  3. Atspausdinkite realų ir rekonstruotą vaizdą
def reconstruct_image(df, image_number = 1):## Part 1: Reshape the image to the correct dimension i.e 1, 1024x_test = df[image_number]x_test_1 = x_test.reshape((1, 32*32))## Part 2: Feed the model with the unseen image, encode/decode the imagewith tf.Session() as sess:sess.run(tf.global_variables_initializer())sess.run(iter.initializer, feed_dict={x: x_test_1,batch_size: 1})## Part 3: Print the real and reconstructed image# Restore variables from disk.saver.restore(sess, "./model.ckpt")print("Model restored.")# Reconstruct imageoutputs_val = outputs.eval()print(outputs_val.shape)fig = plt.figure()# Plot realax1 = fig.add_subplot(121)plot_image(x_test_1, shape=[32, 32], cmap = "Greys_r")# Plot estimatedax2 = fig.add_subplot(122)plot_image(outputs_val, shape=[32, 32], cmap = "Greys_r")plt.tight_layout()fig = plt.gcf()

Dabar, kai vertinimo funkcija yra apibrėžta, galite pamatyti rekonstruoto atvaizdo numerį trylika

reconstruct_image(df =test_x, image_number = 13) 
INFO:tensorflow:Restoring parameters from ./model.ckptModel restored.(1, 1024)

Santrauka

Pagrindinis automatinio kodavimo įrenginio tikslas yra suspausti įvesties duomenis ir tada juos išpakuoti į išvestį, panašią į pirminį.

Autoenkoderio, simetriško su sukamuoju sluoksniu, pavadinimu centrinis, architektūra.

Autokoderį galite sukurti naudodami:

  • Dalinis: norint sukurti tankius sluoksnius su įprasta nuostata:
  • tf.layers.dense,activation=tf.nn.elu,kernel_initializer=xav_init,kernel_regularizer=l2_regularizer
  • dense_layer (): atlikti matricos dauginimą

nuostolių funkciją ir optimizavimą galite apibrėžti:

loss = tf.reduce_mean(tf.square(outputs - features))optimizer = tf.train.AdamOptimizer(learning_rate)train = optimizer.minimize(loss)

Paskutinį kartą vykdykite sesiją, kad mokytumėte modelį.