Wstęp
Delegaci umożliwiają sprzętową akcelerację modeli TensorFlow Lite, wykorzystując akceleratory na urządzeniu, takie jak GPU i procesor sygnału cyfrowego (DSP) .
Domyślnie TensorFlow Lite wykorzystuje jądra procesora zoptymalizowane pod kątem zestawu instrukcji ARM Neon . Jednak procesor jest procesorem wielozadaniowym, który niekoniecznie jest zoptymalizowany pod kątem ciężkiej arytmetyki zwykle występującej w modelach uczenia maszynowego (na przykład matematyki macierzy zaangażowanej w splot i gęste warstwy).
Z drugiej strony większość nowoczesnych telefonów komórkowych zawiera chipy, które lepiej radzą sobie z tymi ciężkimi operacjami. Wykorzystanie ich do operacji w sieciach neuronowych zapewnia ogromne korzyści w zakresie opóźnień i wydajności energetycznej. Na przykład procesory graficzne mogą zapewnić nawet 5- krotne przyspieszenie opóźnienia, podczas gdy procesor Qualcomm® Hexagon DSP wykazał w naszych eksperymentach zmniejszenie zużycia energii nawet o 75%.
Każdy z tych akceleratorów ma powiązane interfejsy API, które umożliwiają niestandardowe obliczenia, takie jak OpenCL lub OpenGL ES dla mobilnego GPU oraz Qualcomm® Hexagon SDK dla DSP. Zazwyczaj trzeba by napisać dużo niestandardowego kodu, aby uruchomić sieć neuronową przez te interfejsy. Sprawy stają się jeszcze bardziej skomplikowane, gdy weźmie się pod uwagę, że każdy akcelerator ma swoje wady i zalety i nie może wykonać każdej operacji w sieci neuronowej. Delegate API TensorFlow Lite rozwiązuje ten problem, działając jako pomost między środowiskiem wykonawczym TFLite a API niższego poziomu.
Wybór delegata
TensorFlow Lite obsługuje wielu delegatów, z których każdy jest zoptymalizowany pod kątem określonych platform i określonych typów modeli. Zwykle będzie wielu delegatów mających zastosowanie do przypadku użycia, w zależności od dwóch głównych kryteriów: docelowej platformy (Android lub iOS?) oraz typu modelu (zmiennoprzecinkowego lub kwantowego?), który próbujesz przyspieszyć .
Delegaci według platformy
Wieloplatformowy (Android i iOS)
- Delegat GPU — delegata GPU można używać zarówno w systemie Android, jak i iOS. Jest zoptymalizowany do uruchamiania modeli 32-bitowych i 16-bitowych typu float, w których dostępny jest procesor graficzny. Obsługuje również 8-bitowe modele skwantowane i zapewnia wydajność GPU porównywalną z ich wersjami float. Aby uzyskać szczegółowe informacje na temat delegata GPU, zobacz TensorFlow Lite na GPU . Aby zapoznać się z samouczkami krok po kroku na temat korzystania z delegata GPU w systemach Android i iOS, zobacz Samouczek delegata GPU TensorFlow Lite .
Android
- Delegat NNAPI dla nowszych urządzeń z systemem Android — Delegat NNAPI może służyć do przyspieszania modeli na urządzeniach z systemem Android z dostępnymi procesorami GPU, DSP i/lub NPU. Jest dostępny w systemie Android 8.1 (API 27+) lub nowszym. Aby zapoznać się z omówieniem delegata NNAPI, instrukcjami krok po kroku i najlepszymi praktykami, zobacz delegata NNAPI TensorFlow Lite .
- Delegat Hexagon dla starszych urządzeń z systemem Android — delegat Hexagon może służyć do przyspieszania modeli na urządzeniach z systemem Android za pomocą Qualcomm Hexagon DSP. Może być używany na urządzeniach ze starszymi wersjami Androida, które nie obsługują NNAPI. Zobacz delegata TensorFlow Lite Hexagon , aby uzyskać więcej informacji.
iOS
- Pełnomocnik Core ML dla nowszych iPhone'ów i iPadów — w przypadku nowszych iPhone'ów i iPadów, na których jest dostępny Neural Engine, możesz użyć pełnomocnika Core ML do przyspieszenia wnioskowania dla 32-bitowych lub 16-bitowych modeli zmiennoprzecinkowych. Neural Engine jest dostępny dla urządzeń mobilnych Apple z A12 SoC lub wyższym. Aby zapoznać się z omówieniem delegata Core ML i instrukcjami krok po kroku, zobacz Delegat TensorFlow Lite Core ML .
Delegaci według typu modelu
Każdy akcelerator został zaprojektowany z myślą o określonej szerokości bitowej danych. Jeśli udostępnisz model zmiennoprzecinkowy delegatowi, który obsługuje tylko 8-bitowe operacje kwantowe (takie jak delegat Hexagon ), odrzuci on wszystkie swoje operacje, a model będzie działał całkowicie na procesorze. Aby uniknąć takich niespodzianek, poniższa tabela zawiera przegląd obsługi delegatów na podstawie typu modelu:
Typ modelu | GPU | NNAPI | Sześciokąt | CoreML |
---|---|---|---|---|
Liczba zmiennoprzecinkowa (32 bity) | TAk | TAk | Nie | TAk |
Kwantyzacja po treningu float16 | TAk | Nie | Nie | TAk |
Kwantyzacja zakresu dynamicznego po treningu | TAk | TAk | Nie | Nie |
Kwantyzacja liczb całkowitych po treningu | TAk | TAk | TAk | Nie |
Szkolenie uwzględniające kwantyzację | TAk | TAk | TAk | Nie |
Sprawdzanie wydajności
Informacje zawarte w tej sekcji stanowią ogólne wytyczne dotyczące tworzenia krótkiej listy delegatów, którzy mogą ulepszyć aplikację. Należy jednak pamiętać, że każdy pełnomocnik ma wstępnie zdefiniowany zestaw obsługiwanych operacji i może działać inaczej w zależności od modelu i urządzenia; na przykład delegat NNAPI może zdecydować się na korzystanie z Edge-TPU Google na telefonie Pixel podczas korzystania z DSP na innym urządzeniu. W związku z tym zwykle zaleca się wykonanie analizy porównawczej, aby ocenić, jak przydatny jest pełnomocnik dla Twoich potrzeb. Pomaga to również uzasadnić wzrost rozmiaru binarnego związany z dołączaniem delegata do środowiska wykonawczego TensorFlow Lite.
TensorFlow Lite oferuje rozbudowane narzędzia do oceny wydajności i dokładności, które mogą zapewnić programistom pewność korzystania z delegatów w swoich aplikacjach. Narzędzia te omówiono w następnej sekcji.
Narzędzia do oceny
Opóźnienia i ślad pamięci
Narzędzie do testów porównawczych TensorFlow Lite może być używane z odpowiednimi parametrami do oszacowania wydajności modelu, w tym średniego opóźnienia wnioskowania, obciążenia inicjalizacji, zużycia pamięci itp. To narzędzie obsługuje wiele flag, aby określić najlepszą konfigurację delegata dla modelu. Na przykład --gpu_backend=gl
można określić za pomocą --use_gpu
, aby zmierzyć wykonanie GPU za pomocą OpenGL. Pełna lista obsługiwanych parametrów delegatów jest zdefiniowana w szczegółowej dokumentacji .
Oto przykład uruchomienia dla modelu skwantyzowanego z GPU przez adb
:
adb shell /data/local/tmp/benchmark_model \
--graph=/data/local/tmp/mobilenet_v1_224_quant.tflite \
--use_gpu=true
Możesz pobrać gotową wersję tego narzędzia dla Androida, 64-bitową architekturę ARM tutaj ( więcej szczegółów ).
Dokładność i poprawność
Delegaci zwykle wykonują obliczenia z inną dokładnością niż ich odpowiedniki procesora CPU. W rezultacie istnieje (zwykle niewielki) kompromis dotyczący dokładności związany z wykorzystaniem delegata do przyspieszania sprzętowego. Zauważ, że nie zawsze tak jest; na przykład, ponieważ GPU używa precyzji zmiennoprzecinkowej do uruchamiania modeli skwantowanych, może wystąpić niewielka poprawa precyzji (np. <1% poprawa Top-5 w klasyfikacji obrazów ILSVRC).
TensorFlow Lite ma dwa rodzaje narzędzi do mierzenia, jak dokładnie zachowuje się delegat dla danego modelu: oparte na zadaniach i niezależne od zadań . Wszystkie narzędzia opisane w tej sekcji obsługują zaawansowane parametry delegowania używane przez narzędzie do analizy porównawczej z poprzedniej sekcji. Zwróć uwagę, że poniższe podsekcje koncentrują się na ocenie delegata (Czy delegat działa tak samo jak procesor?), a nie na ocenie modelu (Czy sam model jest dobry do zadania?).
Ocena zadaniowa
TensorFlow Lite posiada narzędzia do oceny poprawności dwóch zadań opartych na obrazach:
ILSVRC 2012 (klasyfikacja obrazu) z najwyższą dokładnością K
Wykrywanie obiektów COCO (z ramkami ograniczającymi) ze średnią precyzją (mAP)
Gotowe binaria tych narzędzi (Android, architektura 64-bit ARM) wraz z dokumentacją można znaleźć tutaj:
Poniższy przykład pokazuje ocenę klasyfikacji obrazów za pomocą NNAPI z wykorzystaniem Edge-TPU Google na 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
Oczekiwany wynik to lista danych Top-K od 1 do 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
Ocena niezależna od zadania
W przypadku zadań, w których nie ma ustalonego narzędzia oceny na urządzeniu, lub jeśli eksperymentujesz z modelami niestandardowymi, TensorFlow Lite ma narzędzie Inference Diff . (Android, binarna architektura 64-bitowa ARM tutaj )
Wnioskowanie Diff porównuje wykonanie TensorFlow Lite (pod względem opóźnienia i odchylenia wartości wyjściowej) w dwóch ustawieniach:
- Wnioskowanie procesora jednowątkowego
- Wnioskowanie zdefiniowane przez użytkownika — zdefiniowane przez te parametry
Aby to zrobić, narzędzie generuje losowe dane Gaussa i przekazuje je przez dwa interpretery TFLite - jeden z jednowątkowym jądrem procesora, a drugi sparametryzowany przez argumenty użytkownika.
Mierzy opóźnienie obu, a także bezwzględną różnicę między tensorami wyjściowymi z każdego interpretera, na podstawie elementu.
W przypadku modelu z jednym tensorem wyjściowym wynik może wyglądać tak:
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
Oznacza to, że dla tensora wyjścia o indeksie 0
, elementy wyjścia CPU różnią się od wyjścia delegata średnio o 1.96e-05
.
Zauważ, że interpretacja tych liczb wymaga głębszej znajomości modelu i tego, co oznacza każdy tensor wyjścia. Jeśli jest to prosta regresja, która określa jakiś rodzaj wyniku lub osadzenia, różnica powinna być niewielka (w przeciwnym razie jest to błąd delegata). Jednak dane wyjściowe, takie jak „klasa wykrywania” z modeli SSD, są nieco trudniejsze do zinterpretowania. Na przykład może pokazać różnicę przy użyciu tego narzędzia, ale może to nie oznaczać, że coś jest naprawdę nie tak z delegatem: rozważ dwie (fałszywe) klasy: „TV (ID: 10)”, „Monitor (ID: 20)” — jeśli delegat nieco odbiega od złotej prawdy i pokazuje monitor zamiast telewizora, różnica wyjściowa dla tego tensora może wynosić nawet 20-10 = 10.