it-swarm-es.tech

¿Cómo evitar que tensorflow asigne la totalidad de una memoria de GPU?

Trabajo en un entorno en el que se comparten recursos computacionales, es decir, tenemos algunas máquinas servidor equipadas con algunas GPU Nvidia Titan X cada una.

Para modelos de tamaño pequeño a moderado, los 12 GB del Titan X suelen ser suficientes para que 2 o 3 personas entrenen simultáneamente en la misma GPU. Si los modelos son lo suficientemente pequeños como para que un solo modelo no aproveche al máximo todas las unidades computacionales del Titan X, esto puede resultar en una aceleración en comparación con la ejecución de un proceso de entrenamiento tras otro. Incluso en los casos en que el acceso simultáneo a la GPU ralentiza el tiempo de entrenamiento individual, todavía es bueno tener la flexibilidad de tener varios usuarios ejecutando cosas en las GPU a la vez.

El problema con TensorFlow es que, de forma predeterminada, asigna la cantidad total de memoria disponible en la GPU cuando se inicia. Incluso para una pequeña red neuronal de 2 capas, veo que los 12 GB del Titan X están agotados.

¿Hay alguna forma de hacer que TensorFlow solo asigne, por ejemplo, 4 GB de memoria de GPU, si se sabe que esa cantidad es suficiente para un modelo determinado?

215
Fabien C.

Puede configurar la fracción de memoria de GPU que se asignará cuando construya un tf.Session pasando un tf.GPUOptions como parte del argumento config opcional:

# Assume that you have 12GB of GPU memory and want to allocate ~4GB:
gpu_options = tf.GPUOptions(per_process_gpu_memory_fraction=0.333)

sess = tf.Session(config=tf.ConfigProto(gpu_options=gpu_options))

El per_process_gpu_memory_fraction actúa como un límite superior duro en la cantidad de memoria de GPU que utilizará el proceso en cada GPU en la misma máquina. Actualmente, esta fracción se aplica de manera uniforme a todas las GPU en la misma máquina; no hay forma de configurar esto por GPU.

241
mrry
config = tf.ConfigProto()
config.gpu_options.allow_growth=True
sess = tf.Session(config=config)

https://github.com/tensorflow/tensorflow/issues/1578

152
Sergey Demyanov

Aquí hay un extracto del libro Deep Learning with TensorFlow

En algunos casos, es deseable que el proceso solo asigne un subconjunto de la memoria disponible, o que solo aumente el uso de la memoria según lo requiera el proceso. TensorFlow proporciona dos configuraciones opciones en la sesión para controlar esto. La primera es la opción allow_growth, que intenta asignar solo la cantidad de memoria de GPU basada en asignaciones de tiempo de ejecución, comienza asignando muy poca memoria, y cuando las sesiones se ejecutan y se necesita más memoria de GPU, extendemos la región de memoria de GPU que necesita Proceso TensorFlow.

1) Permitir el crecimiento: (más flexible)

config = tf.ConfigProto()
config.gpu_options.allow_growth = True
session = tf.Session(config=config, ...)

El segundo método es la opción per_process_gpu_memory_fraction, que determina la fracción de la cantidad total de memoria que debe asignarse each GPU visible. Nota: No se necesita liberación de memoria, incluso puede empeorar la fragmentación de la memoria cuando se hace.

2) Asignar memoria fija :

Para asignar solo 40% del total de memoria de cada GPU por:

config = tf.ConfigProto()
config.gpu_options.per_process_gpu_memory_fraction = 0.4
session = tf.Session(config=config, ...)

Nota: Eso solo es útil si realmente desea vincular la cantidad de memoria de GPU disponible en el proceso TensorFlow.

33
user1767754

Todas las respuestas anteriores asumen la ejecución con una llamada sess.run(), que se está convirtiendo en la excepción en lugar de la regla en las versiones recientes de TensorFlow.

Cuando se utiliza el marco tf.Estimator (TensorFlow 1.4 y superior), la forma de pasar la fracción a la MonitoredTrainingSession creada implícitamente es

opts = tf.GPUOptions(per_process_gpu_memory_fraction=0.333)
conf = tf.ConfigProto(gpu_options=opts)
trainingConfig = tf.estimator.RunConfig(session_config=conf, ...)
tf.estimator.Estimator(model_fn=..., 
                       config=trainingConfig)

De forma similar en el modo Eager (TensorFlow 1.5 y superior),

opts = tf.GPUOptions(per_process_gpu_memory_fraction=0.333)
conf = tf.ConfigProto(gpu_options=opts)
tfe.enable_eager_execution(config=conf)

Edit: 11-04-2018 Como ejemplo, si va a usar tf.contrib.gan.train, entonces puede usar algo similar a continuación:

tf.contrib.gan.gan_train(........, config=conf)
13
Urs

Actualizado para TensorFlow 2.0 Alpha y más allá

De los documentos Alpha 2.0, la respuesta es ahora solo una línea antes de hacer algo con TensorFlow:

import tensorflow as tf
tf.config.gpu.set_per_process_memory_growth(True)
7
Theo

Enchufe desvergonzado: si instala el Tensorflow compatible con GPU, la sesión asignará primero todas las GPU, ya sea que lo configure para usar solo CPU o GPU. Puedo agregar mi sugerencia de que incluso si configura el gráfico para utilizar la CPU, solo debe configurar la misma configuración (como se responde anteriormente :)) para evitar la ocupación no deseada de la GPU.

Y en la interfaz interactiva como IPython, también debe configurar esa configuración, de lo contrario, asignará toda la memoria y no dejará casi ninguna para otros. Esto a veces es difícil de notar.

3
Lerner Zhang

Bueno, soy nuevo en tensorflow, tengo Geforce 740m o algo GPU con 2GB de ram, estaba ejecutando un ejemplo manuscrito de mnist para un idioma nativo con datos de entrenamiento de 38700 imágenes y 4300 imágenes de prueba y estaba tratando de obtener precisión F1 usando el siguiente código como sklearn no me estaba dando resultados precisos. una vez que agregué esto a mi código existente comencé a recibir errores de GPU.

TP = tf.count_nonzero(predicted * actual)
TN = tf.count_nonzero((predicted - 1) * (actual - 1))
FP = tf.count_nonzero(predicted * (actual - 1))
FN = tf.count_nonzero((predicted - 1) * actual)

prec = TP / (TP + FP)
recall = TP / (TP + FN)
f1 = 2 * prec * recall / (prec + recall)

además, mi modelo era pesado, supongo, estaba recibiendo un error de memoria después de 147, 148 épocas, y luego pensé por qué no crear funciones para las tareas, así que no sé si funciona de esta manera en el flujo de tensión, pero pensé si una variable local es Usado y cuando está fuera de alcance, puede liberar memoria y definí los elementos anteriores para entrenamiento y prueba en módulos, pude lograr 10000 épocas sin ningún problema, espero que esto ayude ...

1
Imran Ud Din

intenté entrenar unet en el conjunto de datos vocales, pero debido al gran tamaño de la imagen, la memoria termina. Probé todos los consejos anteriores, incluso lo intenté con un tamaño de lote == 1, pero no he mejorado. A veces, la versión TensorFlow también causa problemas de memoria. prueba usando

pip instalar tensorflow-gpu == 1.8.0

0
Khan