¡Reserva! Google I / O regresa del 18 al 20 de mayo Regístrese ahora
Se usó la API de Cloud Translation para traducir esta página.
Switch to English

Delegados de TensorFlow Lite

Introducción

Los delegados habilitan la aceleración de hardware de los modelos de TensorFlow Lite al aprovechar los aceleradores en el dispositivo, como la GPU y el Procesador de señal digital (DSP) .

De forma predeterminada, TensorFlow Lite utiliza núcleos de CPU optimizados para el conjunto de instrucciones ARM Neon . Sin embargo, la CPU es un procesador multipropósito que no está necesariamente optimizado para la aritmética pesada que normalmente se encuentra en los modelos de aprendizaje automático (por ejemplo, las matemáticas matriciales involucradas en la convolución y las capas densas).

Por otro lado, la mayoría de los teléfonos móviles modernos contienen chips que son mejores para manejar estas operaciones pesadas. Utilizarlos para operaciones de redes neuronales proporciona enormes beneficios en términos de latencia y eficiencia energética. Por ejemplo, las GPU pueden proporcionar una latencia hasta 5 veces superior , mientras que Qualcomm® Hexagon DSP ha demostrado reducir el consumo de energía hasta en un 75% en nuestros experimentos.

Cada uno de estos aceleradores tiene API asociadas que permiten cálculos personalizados, como OpenCL u OpenGL ES para GPU móviles y Qualcomm® Hexagon SDK para DSP. Normalmente, tendría que escribir mucho código personalizado para ejecutar una red neuronal a través de estas interfaces. Las cosas se complican aún más si se tiene en cuenta que cada acelerador tiene sus pros y sus contras y no puede ejecutar todas las operaciones en una red neuronal. La API delegada de TensorFlow Lite resuelve este problema al actuar como un puente entre el tiempo de ejecución de TFLite y estas API de nivel inferior.

tiempo de ejecución con delegados

Elegir un delegado

TensorFlow Lite admite varios delegados, cada uno de los cuales está optimizado para determinadas plataformas y tipos particulares de modelos. Por lo general, habrá múltiples delegados aplicables a su caso de uso, según dos criterios principales: la plataforma (¿Android o iOS?) A la que se dirige y el tipo de modelo (¿punto flotante o cuantificado?) Que está tratando de acelerar. .

Delegados por Plataforma

Multiplataforma (Android e iOS)

  • Delegado de GPU: el delegado de GPU se puede utilizar tanto en Android como en iOS. Está optimizado para ejecutar modelos basados ​​en flotadores de 32 y 16 bits cuando hay una GPU disponible. También admite modelos cuantificados de 8 bits y proporciona un rendimiento de GPU a la par con sus versiones flotantes. Para obtener detalles sobre el delegado de GPU, consulte TensorFlow Lite en GPU . Para ver tutoriales paso a paso sobre el uso del delegado de GPU con Android e iOS, consulte Tutorial de delegado de GPU de TensorFlow Lite .

Androide

  • Delegado de NNAPI para dispositivos Android más nuevos : el delegado de NNAPI se puede utilizar para acelerar modelos en dispositivos Android con GPU, DSP y / o NPU disponibles. Está disponible en Android 8.1 (API 27+) o superior. Para obtener una descripción general del delegado de NNAPI, instrucciones paso a paso y mejores prácticas, consulte Delegado de NNAPI de TensorFlow Lite .
  • Delegado de Hexagon para dispositivos Android más antiguos : el delegado de Hexagon se puede utilizar para acelerar modelos en dispositivos Android con Qualcomm Hexagon DSP. Se puede usar en dispositivos que ejecutan versiones anteriores de Android que no son compatibles con NNAPI. Consulta el delegado de TensorFlow Lite Hexagon para obtener más detalles.

iOS

  • Delegado de Core ML para iPhones y iPads más nuevos: para iPhones y iPads más nuevos donde Neural Engine está disponible, puede usar el delegado de Core ML para acelerar la inferencia para modelos de punto flotante de 32 o 16 bits. Neural Engine está disponible en dispositivos móviles de Apple con A12 SoC o superior. Para obtener una descripción general del delegado de Core ML e instrucciones paso a paso, consulte Delegado de Core ML de TensorFlow Lite .

Delegados por tipo de modelo

Cada acelerador está diseñado con un cierto ancho de bits de datos en mente. Si proporciona un modelo de punto flotante a un delegado que solo admite operaciones cuantificadas de 8 bits (como el delegado de Hexagon ), rechazará todas sus operaciones y el modelo se ejecutará por completo en la CPU. Para evitar tales sorpresas, la siguiente tabla proporciona una descripción general del soporte de los delegados según el tipo de modelo:

Tipo de modelo GPU NNAPI Hexágono CoreML
Coma flotante (32 bits) No
Cuantificación de float16 posterior al entrenamiento No No
Cuantificación de rango dinámico posterior al entrenamiento No No
Cuantización de enteros posterior al entrenamiento No
Entrenamiento consciente de la cuantificación No

Validando el desempeño

La información en esta sección actúa como una guía aproximada para preseleccionar a los delegados que podrían mejorar su aplicación. Sin embargo, es importante tener en cuenta que cada delegado tiene un conjunto predefinido de operaciones que admite y puede funcionar de manera diferente según el modelo y el dispositivo; por ejemplo, el delegado de NNAPI puede optar por utilizar Edge-TPU de Google en un teléfono Pixel mientras utiliza un DSP en otro dispositivo. Por lo tanto, generalmente se recomienda que realice una evaluación comparativa para evaluar qué tan útil es un delegado para sus necesidades. Esto también ayuda a justificar el aumento de tamaño binario asociado con adjuntar un delegado al tiempo de ejecución de TensorFlow Lite.

TensorFlow Lite cuenta con amplias herramientas de evaluación de precisión y rendimiento que pueden ayudar a los desarrolladores a confiar en el uso de delegados en su aplicación. Estas herramientas se analizan en la siguiente sección.

Herramientas de evaluación

Latencia y huella de memoria

La herramienta de referencia de TensorFlow Lite se puede usar con los parámetros adecuados para estimar el rendimiento del modelo, incluida la latencia de inferencia promedio, la sobrecarga de inicialización, la huella de memoria, etc. Esta herramienta admite varios indicadores para determinar la mejor configuración de delegado para su modelo. Por ejemplo, --gpu_backend=gl se puede especificar con --use_gpu para medir la ejecución de la GPU con OpenGL. La lista completa de parámetros de delegado admitidos se define en la documentación detallada .

A continuación, se muestra un ejemplo de ejecución para un modelo cuantificado con GPU a través de adb :

adb shell /data/local/tmp/benchmark_model \
  --graph=/data/local/tmp/mobilenet_v1_224_quant.tflite \
  --use_gpu=true

Puede descargar la versión prediseñada de esta herramienta para Android, arquitectura ARM de 64 bits aquí ( más detalles ).

Exactitud y corrección

Los delegados suelen realizar cálculos con una precisión diferente a la de sus homólogos de CPU. Como resultado, existe una compensación de precisión (generalmente menor) asociada con la utilización de un delegado para la aceleración de hardware. Tenga en cuenta que esto no siempre es cierto; por ejemplo, dado que la GPU usa precisión de punto flotante para ejecutar modelos cuantificados, puede haber una ligera mejora de precisión (por ejemplo, <1% de mejora de los 5 mejores en la clasificación de imágenes ILSVRC).

TensorFlow Lite tiene dos tipos de herramientas para medir la precisión con la que se comporta un delegado para un modelo determinado: basado en tareas y agnóstico de tareas . Todas las herramientas descritas en esta sección son compatibles con los parámetros de delegación avanzados utilizados por la herramienta de evaluación comparativa de la sección anterior. Tenga en cuenta que las subsecciones siguientes se centran en la evaluación del delegado (¿el delegado se desempeña igual que la CPU?) En lugar de la evaluación del modelo (¿el modelo en sí es bueno para la tarea?).

Evaluación basada en tareas

TensorFlow Lite tiene herramientas para evaluar la corrección en dos tareas basadas en imágenes:

Los binarios prediseñados de estas herramientas (Android, arquitectura ARM de 64 bits), junto con la documentación, se pueden encontrar aquí:

El siguiente ejemplo demuestra la evaluación de clasificación de imágenes con NNAPI utilizando Edge-TPU de Google en un Pixel 4:

adb shell /data/local/tmp/run_eval \
  --model_file=/data/local/tmp/mobilenet_quant_v1_224.tflite \
  --ground_truth_images_path=/data/local/tmp/ilsvrc_images \
  --ground_truth_labels=/data/local/tmp/ilsvrc_validation_labels.txt \
  --model_output_labels=/data/local/tmp/model_output_labels.txt \
  --output_file_path=/data/local/tmp/accuracy_output.txt \
  --num_images=0 # Run on all images. \
  --use_nnapi=true \
  --nnapi_accelerator_name=google-edgetpu

El resultado esperado es una lista de métricas Top-K del 1 al 10:

Top-1 Accuracy: 0.733333
Top-2 Accuracy: 0.826667
Top-3 Accuracy: 0.856667
Top-4 Accuracy: 0.87
Top-5 Accuracy: 0.89
Top-6 Accuracy: 0.903333
Top-7 Accuracy: 0.906667
Top-8 Accuracy: 0.913333
Top-9 Accuracy: 0.92
Top-10 Accuracy: 0.923333

Evaluación agnóstica de tareas

Para tareas en las que no existe una herramienta de evaluación en el dispositivo establecida, o si está experimentando con modelos personalizados, TensorFlow Lite tiene la herramienta Diferencia de inferencia . (Android, arquitectura binaria ARM de 64 bits binaria aquí )

Inference Diff compara la ejecución de TensorFlow Lite (en términos de latencia y desviación del valor de salida) en dos configuraciones:

  • Inferencia de CPU de un solo subproceso
  • Inferencia definida por el usuario: definida por estos parámetros

Para hacerlo, la herramienta genera datos gaussianos aleatorios y los pasa a través de dos intérpretes TFLite: uno que ejecuta núcleos de CPU de un solo subproceso y el otro parametrizado por los argumentos del usuario.

Mide la latencia de ambos, así como la diferencia absoluta entre los tensores de salida de cada intérprete, por elemento.

Para un modelo con un solo tensor de salida, la salida podría verse así:

Num evaluation runs: 50
Reference run latency: avg=84364.2(us), std_dev=12525(us)
Test run latency: avg=7281.64(us), std_dev=2089(us)
OutputDiff[0]: avg_error=1.96277e-05, std_dev=6.95767e-06

Lo que esto significa es que para el tensor de salida en el índice 0 , los elementos de la salida de la CPU difieren de la salida del delegado en un promedio de 1.96e-05 .

Tenga en cuenta que la interpretación de estos números requiere un conocimiento más profundo del modelo y lo que significa cada tensor de salida. Si se trata de una regresión simple que determina algún tipo de puntuación o incrustación, la diferencia debería ser baja (de lo contrario, es un error del delegado). Sin embargo, las salidas como la de 'clase de detección' de los modelos SSD son un poco más difíciles de interpretar. Por ejemplo, puede mostrar una diferencia al usar esta herramienta, pero eso puede no significar algo realmente malo con el delegado: considere dos clases (falsas): "TV (ID: 10)", "Monitor (ID: 20)" - Si un delegado está ligeramente fuera de la verdad dorada y muestra un monitor en lugar de TV, la diferencia de salida para este tensor podría ser tan alta como 20-10 = 10.