Создайте сеть обнаружения объектов SSD

В этом примере показано, как изменить предварительно обученную сеть MobileNet v2 для создания сети обнаружения объектов SSD.

Процедура преобразования предварительно обученной сети в сеть SSD аналогична процедуре передачи обучения для классификации изображений:

  1. Загрузите предварительно обученную сеть.

  2. Выберите один или несколько слоев из предварительно обученной сети для редукции данных.

  3. Удалите все слои после редукции данных слоев

  4. Добавьте новые слои для поддержки задачи обнаружения объектов.

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

Загрузка предварительно обученной сети MobileNet v2 с помощью mobilenetv2. Для этого требуется модель поддержки Deep Learning Toolbox Model для Network™ MobileNet v2. Если этот пакет поддержки не установлен, то функция предоставляет ссылку на загрузку. После загрузки сети преобразуйте сеть в layerGraph объект, чтобы можно было управлять слоями.

net = mobilenetv2();
lgraph = layerGraph(net);

Обновление размера входа сети

Обновите размер входа сети, чтобы соответствовать требованиям к обучающим данным. Для примера предположим, что обучающие данные являются изображениями 300 на 300 RGB. Установите размер входа.

imageInputSize = [300 300 3];

Затем создайте новый входной слой для изображений с таким же именем, как и исходный слой.

imgLayer = imageInputLayer(imageInputSize,"Name","input_1");

Замените старый входной слой изображения новым входным слоем изображения.

lgraph = replaceLayer(lgraph,"input_1",imgLayer);

Выберите слои редукции данных

SSD прогнозирует местоположение объектов с помощью нескольких карт функций. Как правило, вы выбираете слои редукции данных с различными размерами выхода, чтобы использовать преимущества многомасштабных функций. Можно использовать analyzeNetwork функцию или приложение Deep Network Designer, чтобы определить выходные размеры слоев в сети. Обратите внимание, что выбор оптимальных слоев редукции данных набора требует эмпирической оценки.

Для краткости этот пример иллюстрирует использование одного слоя редукции данных. Установите слой редукции данных равным "block_12_add".

featureExtractionLayer = "block_12_add";

Удаление слоев после Редукции данных слоя

Затем удалите слои после редукции данных. Это можно сделать, импортировав сеть в приложение Deep Network Designer, вручную удалив слои и экспортировав измененную сеть в рабочую область.

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

modified = load("mobilenetv2Block12Add.mat");
lgraph = modified.mobilenetv2Block12Add;

Присоединение слоя AnchorBoxLayer

Укажите якорные рамки и количество классов объектов и используйте anchorBoxLayer, чтобы создать слой якорного ящика.

numClasses = 5;

anchorBoxes = [
    16 16
    32 16
    ];

anchorBox = anchorBoxLayer(anchorBoxes,"Name","anchors");

Прикрепите слой якоря к слою редукции данных.

lgraph = addLayers(lgraph,anchorBox);
lgraph = connectLayers(lgraph,"block_12_add","anchors");

Создание ветви классификации твердотельных накопителей

Создайте слой свертки, где количество фильтров свертки равняется numAnchors умножение на numClasses + 1. Дополнительный класс представляет фоновому классу.

numAnchors = size(anchorBoxes,1);
numClassesPlusBackground = numClasses + 1;
numClsFilters = numAnchors * numClassesPlusBackground;
filterSize = 3;
conv = convolution2dLayer(filterSize,numClsFilters,...
    "Name","convClassification",...
    "Padding","same");

Добавьте и соедините слой свертки со слоем якоря.

lgraph = addLayers(lgraph,conv);
lgraph = connectLayers(lgraph,"anchors","convClassification");

Создайте регрессионную ветвь SSD

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

numRegFilters = 4 * numAnchors;
conv = convolution2dLayer(filterSize,numRegFilters,...
    "Name","convRegression",...
    "Padding","same");

Добавьте и соедините слой свертки со слоем якоря.

lgraph = addLayers(lgraph,conv);
lgraph = connectLayers(lgraph,"anchors","convRegression");

Объединить классификационные функции

Создайте ssdMergeLayer инициализировано с количеством классов и количеством слоев редукции данных.

numFeatureExtractionLayers = numel(featureExtractionLayer);
mergeClassification = ssdMergeLayer(numClassesPlusBackground,numFeatureExtractionLayers,...
    "Name","mergeClassification");

Добавьте и соедините слой слияния твердотельных накопителей с convClassification слой.

lgraph = addLayers(lgraph,mergeClassification);
lgraph = connectLayers(lgraph,"convClassification","mergeClassification/in1");

Объедините регрессионные функции

Создайте ssdMergeLayer инициализировано с количеством смещений координат, используемых для уточнения положения якоря, и количеством слоев редукции данных.

numCoordinates = 4;
mergeRegression = ssdMergeLayer(numCoordinates,numFeatureExtractionLayers,...
    "Name","mergeRegression");

Добавьте и соедините слой слияния твердотельных накопителей с convRegression слой.

lgraph = addLayers(lgraph,mergeRegression);
lgraph = connectLayers(lgraph,"convRegression","mergeRegression/in1");

Полная сеть обнаружения твердотельных накопителей

Чтобы завершить классификационную ветвь, создайте и прикрепите слой softmax и слой фокальных потерь.

clsLayers = [
    softmaxLayer("Name","softmax")
    focalLossLayer("Name","focalLoss")
    ];

lgraph = addLayers(lgraph,clsLayers);
lgraph = connectLayers(lgraph,"mergeClassification","softmax");

Чтобы завершить регрессионную ветвь, создайте и присоедините слой прямоугольной регрессии.

reg = rcnnBoxRegressionLayer("Name","boxRegression");

lgraph = addLayers(lgraph,reg);
lgraph = connectLayers(lgraph,"mergeRegression","boxRegression");

Использование analyzeNetwork для проверки сети.

analyzeNetwork(lgraph)

Сеть SSD завершена и может быть обучена с помощью trainSSDObjectDetector функция.