J'obtiens des résultats différents (précision du test) chaque fois que j'exécute l'exemple imdb_lstm.py
à partir du framework Keras ( https://github.com/fchollet/keras/blob/master/examples/imdb_lstm.py ) Le code contient np.random.seed(1337)
en haut, avant toute importation de keras. Cela devrait l'empêcher de générer des numéros différents pour chaque exécution. Qu'est-ce que je rate?
MISE À JOUR: Comment reproduire:
UPDATE2: Je l’utilise sous Windows 8.1 avec MinGW/msys, versions de module:
theano 0.7.0
numpy 1.8.1
scipy 0.14.0c1
UPDATE3: J'ai réduit le problème un peu. Si je lance l'exemple avec GPU (set theeano flag device = gpu0), j'obtiens une précision de test différente à chaque fois, mais si je l'exécute sur un processeur, tout fonctionne comme prévu. Ma carte graphique: NVIDIA GeForce GT 635)
Theano's documentation parle des difficultés liées à l'ensemencement des variables aléatoires et explique pourquoi elles ensemencent chaque instance de graphe avec son propre générateur de nombres aléatoires.
Partage d'un générateur de nombre aléatoire entre différents {{{RandomOp}}} cas, il est difficile de produire le même flux indépendamment de d’autres opérations dans le graphe, et de garder {{{RandomOps}}} isolé . Par conséquent, chaque instance {{{{RandomOp}}} dans un graphique aura son propre propre générateur de nombres aléatoires. Ce générateur de nombres aléatoires est une entrée à la fonction. En utilisation typique, nous utiliserons les nouvelles fonctionnalités de entrées de fonction ({{{valeur}}}, {{{update}}}) à transmettre et à mettre à jour le rng pour chaque {{{RandomOp}}}. En passant les RNG en entrées, il est possible de utilisez les méthodes habituelles d’accès aux entrées de fonction pour accéder à chaque {{{{RandomOp}}} ’rng. Dans cette approche, il n'y a pas de préexistant mécanisme pour travailler avec l'état de nombre aléatoire combiné d'un tout graphique. Il est donc proposé de fournir les fonctionnalités manquantes (les trois dernières exigences.) Via des fonctions auxiliaires: {{{seed, getstate, setstate}}}.
Ils fournissent également des exemples sur la manière d’ensemencer tous les générateurs de nombres aléatoires.
Vous pouvez également ensemencer toutes les variables aléatoires allouées par un RandomStreams par la méthode de départ de cet objet. Cette graine sera utilisé pour créer un générateur de nombre aléatoire temporaire, qui à son tour générer des graines pour chacune des variables aléatoires.
>>> srng.seed(902340) # seeds rv_u and rv_n with different seeds each
J'ai finalement obtenu des résultats reproductibles avec mon code. C'est une combinaison de réponses que j'ai vues sur le web. La première chose est de faire ce que @alex dit:
numpy.random.seed
;PYTHONHASHSEED=0
pour Python 3.Ensuite, vous devez résoudre le problème signalé par @ user2805751 à propos de cuDNN en appelant votre code Keras avec le THEANO_FLAGS
supplémentaire suivant:
dnn.conv.algo_bwd_filter=deterministic,dnn.conv.algo_bwd_data=deterministic
Et enfin, vous devez patcher votre installation Theano selon ce commentaire , qui consiste essentiellement à:
*_dev20
par sa version standard dans theano/sandbox/cuda/opt.py
.Cela devrait vous donner les mêmes résultats pour la même graine.
Notez qu'il peut y avoir un ralentissement. J'ai vu une augmentation de temps d'exécution d'environ 10%.
Vous pouvez trouver la réponse dans la documentation de Keras: https://keras.io/getting-started/faq/#how-can-i-obtain-reproducible-results-using-keras-during-development .
En bref, pour être absolument certain que vous obtiendrez des résultats reproductibles avec votre script python sur le processeur d'un ordinateur portable/portable, vous devrez procéder comme suit:
PYTHONHASHSEED
à une valeur fixepython
à une valeur fixenumpy
à une valeur fixetensorflow
à une valeur fixetensorflow
Après le lien Keras
en haut, le code source que j'utilise est le suivant:
# Seed value
# Apparently you may use different seed values at each stage
seed_value= 0
# 1. Set `PYTHONHASHSEED` environment variable at a fixed value
import os
os.environ['PYTHONHASHSEED']=str(seed_value)
# 2. Set `python` built-in pseudo-random generator at a fixed value
import random
random.seed(seed_value)
# 3. Set `numpy` pseudo-random generator at a fixed value
import numpy as np
np.random.seed(seed_value)
# 4. Set `tensorflow` pseudo-random generator at a fixed value
import tensorflow as tf
tf.set_random_seed(seed_value)
# 5. Configure a new global `tensorflow` session
from keras import backend as K
session_conf = tf.ConfigProto(intra_op_parallelism_threads=1, inter_op_parallelism_threads=1)
sess = tf.Session(graph=tf.get_default_graph(), config=session_conf)
K.set_session(sess)
Il est inutile de dire que vous n'avez pas besoin de spécifier les variables seed
ou random_state
aux fonctions numpy
, scikit-learn
ou tensorflow
/keras
que vous utilisez dans votre script python, car avec le code source ci-dessus, nous définissons globalement leurs générateurs pseudo-aléatoires à une valeur fixe.
J'aimerais ajouter quelque chose aux réponses précédentes. Si vous utilisez python 3 et que vous voulez obtenir des résultats reproductibles à chaque exécution, vous devez
Je suis d'accord avec le commentaire précédent, mais des résultats reproductibles nécessitent parfois le même environnement (par exemple, packages installés, caractéristiques de la machine, etc.). Pour cela, je vous recommande de copier votre environnement à un autre endroit au cas où vous obtiendriez des résultats reproductibles. Essayez d'utiliser l'une des prochaines technologies:
J'ai formé et testé le type de réseaux de neurones Sequential()
à l'aide de Keras. J'ai effectué une régression non linéaire sur des données de parole bruyantes. J'ai utilisé le code suivant pour générer une graine aléatoire:
import numpy as np
seed = 7
np.random.seed(seed)
Je reçois exactement les mêmes résultats avec val_loss
chaque fois que je m'entraîne et que je teste les mêmes données.
Cela fonctionne pour moi:
SEED = 123456
import os
import random as rn
import numpy as np
from tensorflow import set_random_seed
os.environ['PYTHONHASHSEED']=str(SEED)
np.random.seed(SEED)
set_random_seed(SEED)
rn.seed(SEED)