Nvidia Transfer Learning Toolkit - подробное руководство

В современном мире большая часть оптимизированной архитектуры глубоких нейронных сетей уже доступна для использования, и что делает ее более впечатляющей, так это способность обучать только несколько последних слоев предварительно обученной модели для достижения сверхчеловеческой точности за очень короткое время.

В этой статье мы собираемся обучить модель на общедоступном наборе данных KITTI, используя NVIDIA Transfer Learning Toolkit (TLT), и развернуть ее в Jetson Nano.

Первый шаг - настроить учетную запись NVIDIA NGC и вытащить контейнер TLT.

docker pull nvcr.io/nvidia/tlt-streamanalytics:v1.0_py2

После этого вы можете запустить свой контейнер TLT, используя следующую команду.

docker run --runtime=nvidia -it \
   -v /home/<username>/workspace:/workspace \
   -p 8888:8888 tlt-streamanalytics:v1.0_py2

Убедитесь, что вы прикрепили свой локальный системный каталог к ​​контейнеру, это гарантирует, что все данные, которые вы производите во время обучения, будут находиться в вашей локальной системе, а не застрять внутри контейнера.

Мы собираемся провести все наши эксперименты в блокноте jupyter, так что давайте сначала его начнем.

cd /workspace
jupyter notebook --ip 0.0.0.0 --allow-root

После этого вы можете посетить http: // localhost: 8888 в браузере вашей локальной системы, и все готово. Еще одна важная вещь, прежде чем мы начнем фактическую работу, - иметь API_KEY, чтобы делать что-либо с TLT.

Перейдите на https://ngc.nvidia.com/setup, убедитесь, что вы вошли в систему, нажмите кнопку Получить ключ API, сгенерируйте ключ API для себя и храните его где-нибудь, так как он будет требоваться на каждом этапе обучения.

Как только вы окажетесь в блокноте jupyter, приступим к процессу обучения. В первой ячейке кода записной книжки настройте свой API_KEY, чтобы он был доступен на протяжении всего обучения.

Теперь, прежде чем продолжить, давайте убедимся, что у нас есть все необходимые каталоги.

|----workspace
    |---- dataset
    |---- tf_records   
    |---- pretrained_model
    |---- trained_model
    |---- pruned_model
    |---- retrained_model
    |---- exported_model
    |---- spec_files
    |---- scripts

Подготовка набора данных

Набор данных можно скачать здесь https://www.kaggle.com/twaldo/kitti-object-detection/data

Храните его в каталоге рабочая область / набор данных для легкого доступа. После извлечения ZIP-файла вы получите каталоги обучения и тестирования, содержащие изображения и соответствующие им ярлыки. Для простоты этого урока мы будем использовать только обучающие изображения.

Мы можем быстро взглянуть на размер набора обучающих данных:

!echo Total Training Images:
!ls /workspace/dataset/KITTI_original/training/image_2 -l | wc -l
!echo
!echo Total Training Labels:
!ls /workspace/dataset/KITTI_original/training/label_2 -l | wc -l
  • Всего тренировочных изображений: 7482
  • Всего ярлыков обучения: 7482

Также давайте посмотрим на одно из изображений

from IPython.display import display
from PIL import Image
path = '/workspace/dataset/KITTI_original/training/image_2/003945.png'
image = Image.open(path)
display(image)
width, height = image.size
print("HxW: ({}, {})".format(height, width))

Давайте подтвердим, что в нашем файле меток набора данных есть все 15 обязательных столбцов.

!cat /workspace/dataset/KITTI_original/training/label_2/003945.txt

Мы должны убедиться, что все наши обучающие изображения имеют одинаковое разрешение, иначе TLT выдаст ошибку между тренировками.

Хм ... здесь что-то подозрительное, как видите, есть небольшая разница в разрешении некоторых изображений, мы должны это исправить. Мы изменим размеры всех изображений до размеров HxW: 128, 512, одновременно изменяя масштаб их меток.

Причины, по которым мы выбрали эти размеры:

  • Это кратно 16
  • Относительно меньше исходного изображения
  • Имеет соотношение сторон ближе к исходному разрешению.
original HxW: (375, 1242) ==> aspect ratio W/H: 3.32
new HxW: (128, 512) ==> aspect ratio W/H: 4

Мы подготовили небольшой скрипт на Python, который может изменять размер / масштабирование всех изображений / меток до заданного размера вывода, мы преобразовали наши изображения в 128x512 с форматом «.jpg» и сохраняем наш набор данных с измененным размером в новый каталог.

Преобразование набора данных в TFRecords

Согласно TLT Docs, мы должны преобразовать наш набор данных в TFRecords перед обучением, это обеспечивает быстрый и эффективный способ для модели читать набор данных.

Мы преобразуем наш набор данных в TFRecords с помощью команды tlt-dataset-convert, для продолжения нам нужно создать файл спецификации для описания набора данных.

!cat /workspace/spec_files/convert.txt

см. файл спецификации здесь https://rebrand.ly/ypn5ar

После этого мы готовы преобразовать наш набор данных в TFRecords.

!tlt-dataset-convert -d spec_files/convert.txt -o /workspace/tf_records/

Загрузка предварительно обученной модели

Мы можем просмотреть модели, доступные на NGC.

!ngc registry model list *detectnet*

Скачайте выбранную нами модель

!ngc registry model download-version nvidia/iva/tlt_resnet18_detectnet_v2:1 -d /workspace/pretrained_model

Обучение

Теперь мы всего на один шаг отстаем от обучения нашей модели, это самая важная часть всего руководства, то есть подготовка действительного файла спецификации для обучения модели. Согласно официальной документации TLT, файлы спецификации содержат 8 ключевых компонентов, отвечающих за настройку модели для обеспечения хорошей точности:

  1. model_config
  2. bbox_rasterizer_config
  3. cost_function_config
  4. training_config
  5. augmentation_config
  6. postprocessing_config
  7. dataset_config
  8. оценка_конфиг

Подробнее о них можно прочитать здесь: https://docs.nvidia.com/metropolis/TLT/tlt-getting-started-guide/index.html#spec_file_gridbox_topic

Вот как выглядит наш файл спецификаций обучения

!cat /workspace/spec_files/train.txt

см. файл спецификации здесь https://rebrand.ly/9kbu1z

Наконец, мы можем приступить к обучению нашей модели.

!tlt-train detectnet_v2 -e spec_files/train.txt \
    -r /workspace/trained_model --gpus 5 -k $API_KEY

Оценка

Если вы хотите быть вдвойне уверены в точности модели, вы можете оценить тестовый набор данных.

!tlt-evaluate detectnet_v2 -e spec_files/train.txt \
    -m "/workspace/trained_model/model.step-9600.tlt" \
    -k $API_KEY

Вывод

Это тот захватывающий момент, когда мы увидим нашу модель в действии, да, теперь мы можем ожидать, что наша модель будет рисовать эти поверхностные ограничивающие рамки. Перед этим нам нужно подготовить наш файл спецификации вывода.

Вот как выглядит наш файл спецификации вывода

!cat /workspace/spec_files/infer.txt

см. файл спецификации здесь https://rebrand.ly/5b780

Теперь, когда у нас подготовлен файл спецификации вывода, мы можем использовать нашу модель для вывода, мы используем некоторые изображения с разным разрешением, которые еще не присутствуют в нашем наборе данных. Надеюсь на лучшее!

!tlt-infer detectnet_v2 \
    -m "/workspace/trained_model/model.step-9600.tlt" \
    -i /workspace/dataset/test_image \
    -o /workspace/inferred_images \
    -k $API_KEY \
    -bs 16 \
    -cp spec_files/infer.txt

Визуализация изображений

TLT принимает входные данные из каталога и сохраняет предполагаемые изображения в указанном выходном каталоге, чтобы увидеть эти изображения, мы должны загрузить их так же, как и раньше.

from IPython.display import display
from PIL import Image
path = '/workspace/inferred_images/images_annotated/car001_720x1280.jpg'
image = Image.open(path)
display(image)
width, height = image.size
print("HxW: ({}, {})".format(height, width))
path = '/workspace/inferred_images/images_annotated/car001_128x512.jpg'
image = Image.open(path)
display(image)
width, height = image.size
print("HxW: ({}, {})".format(height, width))

Ах! в этот удивительный момент, видите ли, мы обучили нашу модель всего за 120 эпох, что едва ли заняло 35 минут, и она может обнаруживать автомобили на изображениях, что уже больше, чем я ожидал до сих пор.

Обрезка

После обрезки мы можем снова переобучить эту обрезанную модель, чтобы сохранить точность, уменьшая размер модели и время вывода.

!tlt-prune -pm "/workspace/trained_model/model.step-9600.tlt" \
    -o "/workspace/pruned_model" -pth 0.30 -nf 16 \
    -k $API_KEY

После обрезки очень важно переобучить нашу модель для повышения производительности, но нам нужно сначала создать наш файл спецификации переобучения, не волнуйтесь, просто сделайте копию ранее созданного файла спецификации обучения и замените путь к файлу весов старой предварительно обученной модели на наша недавно обученная модель весит путь к файлу.

Так выглядит наш файл спецификаций по переобучению

!cat /workspace/spec_files/retrain.txt

см. файл спецификации здесь https://rebrand.ly/fcot8y

Создав файл спецификации повторного обучения, мы можем приступить к повторному обучению нашей модели.

!tlt-train detectnet_v2 -e "/workspace/spec_files/retrain.txt" \
    -r "/workspace/retrained_model" --gpus 5 -k $API_KEY

Экспорт модели

Несомненно, наша модель превзошла наши ожидания, но все еще можно верить в среду TLT, что модель действительно работает в соответствии с нашими ожиданиями и может использоваться с нашими периферийными устройствами, которые нам нужны для ее экспорта.

Для экспорта модели доступны три варианта:

  • FP16
  • FP32
  • INT8

Мы собираемся экспортировать с помощью INT8, для экспорта в INT8 необходимо сгенерировать файл калибровки.

!tlt-int8-tensorfile detectnet_v2 -e spec_files/retrain.txt \
        -o exported_model/calibration.tensor -m 20

Теперь мы готовы экспортировать нашу модель.

!tlt-export "/workspace/retrained_model/model.step-9600.tlt" \
    -k $API_KEY \
    --export_module detectnet_v2 \
    --outputs output_bbox/BiasAdd,output_cov/Sigmoid \
    --data_type int8  \
    --output_file exported_model/smchyd_demo_model.etlt \
    --cal_data_file exported_model/calibration.tensor \
    --cal_cache_file exported_model/calibration.bin \
    --input_dims 3,128,512

Если вы хотите экспортировать с FP16 или FP32, используйте следующие команды:

FP16

!tlt-export "/workspace/retrained_model/model.step-9600.tlt" \
            -k $API_KEY \
            --export_module detectnet_v2 \
            --outputs output_bbox/BiasAdd,output_cov/Sigmoid \
            --data_type fp16 \
            --output_file exported_model/smchyd_demo_model.etlt

FP32

!tlt-export "/workspace/retrained_model/model.step-9600.tlt" \
            -k $KEY \
            --export_module detectnet_v2 \
            --outputs output_bbox/BiasAdd,output_cov/Sigmoid \
            --data_type fp32 \
            --output_file exported_model/smchyd_demo_model.etlt

Таким образом, мы успешно экспортировали нашу модель.

Чтобы использовать нашу модель с глубоким потоком, нам нужно создать 3 файла:

  1. label.txt
  2. Primary_inference.txt
  3. stream_config.txt

Вам нужно будет немного изменить эти файлы в соответствии с конфигурацией вашей модели, то есть входными размерами, порогом и т. Д.

загрузите эти файлы здесь https://rebrand.ly/3715a

После этого последний шаг - переместить эти файлы, сгенерированные внутри «/ workspace / exported_model», и 3 трех файла, о которых мы говорили выше, на наше граничное устройство и использовать приложение tlt-converter для преобразования нашей модели в соответствии с конфигурацией нашего устройства jetson, чтобы она была в состоянии нормально работать.

Чтобы переместить экспортированную модель в наш Jetson Nano, мы сначала создадим каталог, в котором мы будем хранить нашу модель и связанные с ней файлы конфигурации. Итак, подключитесь к устройству по SSH и создайте требуемый каталог.

nitin@ThinkPad:~ ssh [email protected]
[email protected]’s password:
welcome to ubuntu 18.04.3 LTS
nano@nano-desktop:~ mkdir TLT_DEMO

Теперь, наконец, мы переместим нашу модель на nano, откроем другой терминал и переместим файлы с помощью команды SCP. Я сделал архив для файлов, чтобы их было легче переместить, или вы можете вручную переместить эти файлы на свое пограничное устройство. После перемещения файлов просто извлеките его туда.

Запустите DeepStream (на Jetson)

Загрузите tlt-конвертер на пограничное устройство с https://developer.download.nvidia.com/assets/TLT/Public/TLT_Converter.zip

Поскольку мы собираемся преобразовать нашу модель, нам также понадобится каталог для хранения наших файлов конфигурации глубокого потока. Создайте его с помощью mkdir ds_configs.

Теперь сконвертируем нашу модель

sudo ./tlt-converter -k $KEY -d 3,128,512 \
        -o output_bbox/BiasAdd,output_cov/Sigmoid \
        -e ~/TLT_DEMO/ds_configs/INT8_m1.plan \
        -t int8 \
        -c ~/TLT_DEMO/calibration.bin \
        -m 1 \
        ~/TLT_DEMO/smchyd_demo_model.etlt

Наконец, после этого мы готовы запустить наш вывод. В конфигурационных файлах требуются лишь небольшие изменения.

Кроме того, не забудьте переместить все файлы моделей, относящиеся к глубокому потоку, в каталог ds_configs, включая сгенерированную модель, поскольку их хранение в одном каталоге помогает снизить вероятность ошибки из-за неправильной настройки путей.

Вот окончательная сводка файлов, присутствующих в соответствующих каталогах, прежде чем мы запустим нашу модель.

Пожалуйста, поместите их в правильный каталог, если еще не сделали этого. Теперь мы готовы запустить нашу модель, убедитесь, что у вас есть монитор, подключенный к вашему пограничному устройству, оставайтесь в каталоге ds_configs и запустите

deepstream-app -c stream_config.txt

И БУМ! Наша модель начала предсказывать метки обученных объектов.

Вот ссылка на блокнот jupyter https://rebrand.ly/tl4k1h, который используется для обучения модели.

О Sentinel

Sentinel - это аппаратная платформа на базе Nvidia NX / Nano, которая может запускать несколько современных моделей глубокого обучения и обеспечивать поддержку интеллектуальной видеоаналитики на периферии.

Вы можете узнать больше о Sentinel на странице продукта https://smartcow.ai/products/sentinel.html

Вот параллельное сравнение Sentinel и Nano.

Важная статистика

Ключевые особенности TLT

  • Предварительно обученные веса, оптимизированные для графического процессора, для задач компьютерного зрения
  • Легко изменять файлы конфигурации для добавления новых классов и переобучения моделей с пользовательскими данными
  • Уменьшайте размеры модели с помощью функции обрезки

Особая благодарность: Эдди Сеймуру, Випул Амин, Чарбел Аун, Моргану Хуангу.

Author
Nitin Rai
Jr. ML Engineer at SmartCow, Responsible for Rapid Prototyping

Ссылка:

Форум разработчиков https://rebrand.ly/3xr6ts