В этом примере показано, как создать код C из функции MATLAB ®, которая классифицирует изображения цифр с использованием обученной модели классификации. В этом примере демонстрируется альтернативный рабочий процесс классификации цифр с использованием функций HOG (Computer Vision Toolbox). Однако для поддержки создания кода в этом примере можно выполнить шаги создания кода в этом примере.
Автоматизированная классификация изображений является повсеместным инструментом. Например, обученный классификатор может быть развернут на беспилотнике для автоматического выявления аномалий на суше в отснятых кадрах или на машине, которая сканирует рукописные почтовые коды на письмах. В последнем примере после того, как машина найдет почтовый индекс и сохранит отдельные изображения цифр, развернутый классификатор должен угадать, какие цифры находятся в изображениях, чтобы восстановить почтовый индекс.
В этом примере показано, как обучить и оптимизировать мультиклассовую модель классификации выходных кодов с исправлением ошибок (ECOC) для классификации цифр на основе интенсивности пикселей в растровых изображениях. Модель ECOC содержит учеников бинарного вектора поддержки (SVM). Затем в этом примере показано, как создать код C, который использует обученную модель для классификации новых изображений. Данные представляют собой синтетические изображения деформированных цифр различных шрифтов, которые имитируют рукописные цифры.
Для создания кода C/C + + необходимо иметь доступ к компилятору C/C + +, который настроен правильно. MATLAB Coder™ находит и использует поддерживаемый установленный компилятор. Вы можете использоватьmex -setup для просмотра и изменения компилятора по умолчанию. Дополнительные сведения см. в разделе Изменение компилятора по умолчанию.
Для генерации кода C используется кодер MATLAB:
Требуется правильно настроенный компилятор.
Требуется, чтобы поддерживаемые функции находились в определяемой функции MATLAB. Базовый рабочий процесс см. в разделе Введение в создание кода.
Запрещает объекты в качестве входных аргументов определенной функции.
Что касается последнего ограничения, то следует учитывать, что:
Обученные модели классификации являются объектами
Поддержка кодера MATLAB predict для классификации наблюдений с использованием обученных моделей, но не поддерживает подгонку модели
Чтобы обойти ограничения генерации кода для классификации, обучайте модель классификации с помощью MATLAB, а затем передайте результирующий объект модели в saveLearnerForCoder. saveLearnerForCoder функция удаляет некоторые свойства, которые не требуются для прогнозирования, а затем сохраняет обученную модель на диск в виде массива структуры. Как и модель, структурный массив содержит информацию, используемую для классификации новых наблюдений.
После сохранения модели на диск загрузите ее в функцию MATLAB с помощью loadLearnerForCoder. loadLearnerForCoder функция загружает сохраненный массив структуры, а затем реконструирует объект модели. В функции MATLAB для классификации наблюдений можно передать модель и набор данных предиктора, который может быть входным аргументом функции, в predict.
Перед развертыванием классификатора образов на устройстве:
Получите достаточное количество помеченных изображений.
Выберите элементы для извлечения из изображений.
Подготовка и оптимизация классификационной модели. Этот шаг включает в себя выбор соответствующего алгоритма и настройку гиперпараметров, то есть параметров модели, не подходящих во время обучения.
Сохранение модели на диск с помощью saveLearnerForCoder.
Определите функцию для классификации новых изображений. Функция должна загрузить модель с помощью loadLearnerForCoderи может возвращать метки, такие как оценки классификации.
Настройте компилятор Си.
Определите среду для выполнения созданного кода.
Создайте код C для функции.
Загрузить digitimages набор данных.
load digitimagesimages множество 28 на 28 на 3000 uint16 целые числа. Каждая страница представляет собой растровое изображение цифры. Каждый элемент имеет пиксельную интенсивность. Соответствующие метки находятся в числовом векторе 3000 на 1 Y. Для получения дополнительной информации введите Description в командной строке.
Запишите количество наблюдений и число переменных предиктора. Создайте раздел данных, определяющий удержание 20% данных. Извлеките индексы обучающего и тестового наборов из раздела данных.
rng(1) % For reproducibility n = size(images,3); p = numel(images(:,:,1)); cvp = cvpartition(n,'Holdout',0.20); idxTrn = training(cvp); idxTest = test(cvp);
Отображение девяти случайных изображений из данных.
figure for j = 1:9 subplot(3,3,j) selectImage = datasample(images,1,3); imshow(selectImage,[]) end

Поскольку интенсивности необработанных пикселей сильно различаются, следует нормализовать их значения перед обучением классификационной модели. Масштабировать интенсивности пикселей так, чтобы они находились в интервале [0,1]. То есть предположим, что - интенсивность пикселя в изображении. Для изображения масштабируйте все его интенсивности пикселя, используя следующую формулу:
pij).
X = double(images); for i = 1:n minX = min(min(X(:,:,i))); maxX = max(max(X(:,:,i))); X(:,:,i) = (X(:,:,i) - minX)/(maxX - minX); end
Кроме того, при наличии лицензии на Toolbox™ обработки изображений можно эффективно масштабировать интенсивности пикселей изображений до [0,1] с помощью mat2gray. Дополнительные сведения см. в разделе mat2gray(Панель инструментов обработки изображений).
Для генерации кода данные предиктора для обучения должны быть в таблице числовых переменных или числовой матрице.
Преобразование данных в матрицу таким образом, чтобы переменные предиктора (интенсивности пикселей) соответствовали столбцам, а изображения (наблюдения) - строкам. Поскольку reshape принимает элементы по столбцам, необходимо транспонировать их результат.
X = reshape(X,[p,n])';
Для того чтобы предварительная обработка данных поддерживала изображение, постройте график первого наблюдения в X.
figure imshow(reshape(X(1,:),sqrt(p)*[1 1]),[],'InitialMagnification','fit')

Computer Vision Toolbox™ предлагает несколько методов извлечения функций для изображений. Одной из таких методик является извлечение гистограммы признаков ориентированного градиента (HOG). Сведения о том, как обучить модель ECOC с использованием функций HOG, см. в разделе Классификация цифр с использованием функций HOG (Computer Vision Toolbox). Дополнительные сведения о других поддерживаемых методах см. в разделе Обнаружение и извлечение локальных функций (панель инструментов Computer Vision Toolbox). В этом примере в качестве переменных предиктора используются масштабированные интенсивности пикселей.
Линейные модели SVM часто применяются к наборам данных изображения для классификации. Однако SVM являются двоичными классификаторами, и в наборе данных имеется 10 возможных классов.
Можно создать многоклассовую модель из нескольких двоичных учеников SVM с помощью fitcecoc. fitcecoc объединяет несколько двоичных учеников, используя схему кодирования. По умолчанию fitcecoc применяет конструкцию «один против одного», которая определяет обучающих бинарных учеников на основе наблюдений из всех комбинаций пар классов. Например, в проблеме с 10 классами, fitcecoc должен обучить 45 бинарных моделей SVM.
Как правило, при обучении модели классификации следует настраивать гиперпараметры до тех пор, пока не будет достигнута удовлетворительная ошибка обобщения. Таким образом, следует выполнить перекрестную проверку моделей для определенных наборов гиперпараметров, а затем сравнить показатели ошибочной классификации.
Можно выбрать собственные наборы значений гиперпараметров или указать для реализации байесовской оптимизации. (Общие сведения о байесовской оптимизации см. в разделе Рабочий процесс байесовской оптимизации.) В этом примере выполняется перекрестная проверка выбранной сетки значений.
Для перекрестной проверки модели ECOC двоичных учеников SVM на основе результатов обучения используйте пятикратную перекрестную проверку. Хотя значения предиктора имеют одинаковый диапазон, чтобы избежать численных трудностей во время обучения, стандартизируйте предикторы. Также оптимизируйте конструкцию кодирования ECOC и ограничение блока SVM. Используйте все комбинации этих значений:
Для проектирования кодирования ECOC используйте «один против одного» и «один против всех».
Для ограничения поля SVM используйте три логарифмически разнесенных значения от 0,1 до 100.
Для всех моделей сохраните 5-кратные показатели перекрестной проверки ошибочной классификации.
coding = {'onevsone' 'onevsall'};
boxconstraint = logspace(-1,2,3);
cvLoss = nan(numel(coding),numel(boxconstraint)); % For preallocation
for i = 1:numel(coding)
for j = 1:numel(boxconstraint)
t = templateSVM('BoxConstraint',boxconstraint(j),'Standardize',true);
CVMdl = fitcecoc(X(idxTrn,:),Y(idxTrn),'Learners',t,'KFold',5,...
'Coding',coding{i});
cvLoss(i,j) = kfoldLoss(CVMdl);
fprintf('cvLoss = %f for model using %s coding and box constraint=%f\n',...
cvLoss(i,j),coding{i},boxconstraint(j))
end
endcvLoss = 0.052083 for model using onevsone coding and box constraint=0.100000 cvLoss = 0.055000 for model using onevsone coding and box constraint=3.162278 cvLoss = 0.050000 for model using onevsone coding and box constraint=100.000000 cvLoss = 0.116667 for model using onevsall coding and box constraint=0.100000 cvLoss = 0.123750 for model using onevsall coding and box constraint=3.162278 cvLoss = 0.125000 for model using onevsall coding and box constraint=100.000000
Определите индексы гиперпараметров, которые дают минимальный коэффициент неправильной классификации. Обучение модели ECOC с использованием данных обучения. Стандартизация обучающих данных и предоставление оптимальной комбинации гиперпараметров.
minCVLoss = min(cvLoss(:))
minCVLoss = 0.0500
linIdx = find(cvLoss == minCVLoss);
[bestI,bestJ] = ind2sub(size(cvLoss),linIdx);
bestCoding = coding{bestI}bestCoding = 'onevsone'
bestBoxConstraint = boxconstraint(bestJ)
bestBoxConstraint = 100
t = templateSVM('BoxConstraint',bestBoxConstraint,'Standardize',true); Mdl = fitcecoc(X(idxTrn,:),Y(idxTrn),'Learners',t,'Coding',bestCoding);
Создайте матрицу путаницы для изображений тестового набора.
testImages = X(idxTest,:); testLabels = predict(Mdl,testImages); confusionMatrix = confusionchart(Y(idxTest),testLabels);

Диагональные и внедиагональные элементы соответствуют корректно и неправильно классифицированным наблюдениям соответственно. Mdl кажется, правильно классифицирует большинство изображений.
Если вы удовлетворены работой Mdl, затем можно продолжить создание кода для прогнозирования. В противном случае можно продолжить настройку гиперпараметров. Например, можно попробовать обучить слушателей SVM с помощью различных функций ядра.
Mdl является прогностической классификационной моделью, но ее необходимо подготовить для создания кода. Сохранить Mdl в текущий рабочий каталог с помощью saveLearnerForCoder.
saveLearnerForCoder(Mdl,'DigitImagesECOC')saveLearnerForCoder уплотняет Mdl, преобразует его в массив структуры и сохраняет в MAT-файле DigitImagesECOC.mat.
Определение функции точки входа с именем predictDigitECOC.m это делает следующее:
Включить директиву создания кода %#codegen где-то в функции.
Принять данные изображения, соответствующие X.
Груз DigitImagesECOC.mat использование loadLearnerForCoder.
Возврат прогнозируемых меток.
type predictDigitECOC.m % Display contents of predictDigitECOC.m file
function label = predictDigitECOC(X) %#codegen
%PREDICTDIGITECOC Classify digit in image using ECOC Model
% PREDICTDIGITECOC classifies the 28-by-28 images in the rows of X using
% the compact ECOC model in the file DigitImagesECOC.mat, and then
% returns class labels in label.
CompactMdl = loadLearnerForCoder('DigitImagesECOC.mat');
label = predict(CompactMdl,X);
end
Примечание.Если нажать кнопку, расположенную в правом верхнем разделе этой страницы, и открыть этот пример в MATLAB, то MATLAB откроет папку примеров. Эта папка содержит файл функции начального уровня.
Убедитесь, что функция прогнозирования возвращает те же метки тестового набора, что и predict.
pfLabels = predictDigitECOC(testImages); verifyPF = isequal(pfLabels,testLabels)
verifyPF = logical
1
isequal возвращает логический 1 (true), что означает, что все входы равны. predictDigitECOC дает ожидаемые результаты.
Сгенерированный код может выполняться:
Внутри среды MATLAB в виде файла C-MEX
Вне среды MATLAB в качестве автономного исполняемого файла
Вне среды MATLAB в качестве общей утилиты, связанной с другим автономным исполняемым файлом
В этом примере создается файл MEX для выполнения в среде MATLAB. Создание такого MEX-файла позволяет протестировать сгенерированный код с помощью инструментов MATLAB перед развертыванием функции вне среды MATLAB. В функцию MEX можно включить код для проверки, но не для генерации кода, объявив команды как внешние с помощью coder.extrinsic (Кодер MATLAB). Внешние команды могут включать функции, не поддерживающие генерацию кода. Все внешние команды в функции MEX выполняются в MATLAB, но codegen не создает для них код.
Если планируется развертывание кода вне среды MATLAB, необходимо создать автономный исполняемый файл. Одним из способов указать выбор компилятора является использование -config вариант codegen. Например, чтобы создать статический исполняемый файл C, укажите -config:exe при звонке codegen. Дополнительные сведения о настройке параметров генерации кода см. в разделе -config вариант codegen (Кодер MATLAB).
Собрать predictDigitECOC.m в файл MEX с использованием codegen. Укажите следующие параметры:
-report - Создает отчет о компиляции, который идентифицирует исходный код MATLAB и связанные файлы, которые codegen создается во время создания кода.
-args - Кодер MATLAB требует указания свойств всех входных аргументов функции. Один из способов сделать это - предоставить codegen с примером входных значений. Следовательно, кодер MATLAB выводит свойства из значений примера. Укажите изображения тестового набора, соответствующие X.
codegen predictDigitECOC -report -args {testImages}
Code generation successful: View report
codegen успешно сгенерирован код для функции прогнозирования. Отчет можно просмотреть, нажав кнопку View report ссылку или путем ввода open('codegen/mex/predictDigitECOC/html/report.mldatx') в окне команд. В случае неуспешного создания кода отчет может помочь в отладке.
codegen создает каталог pwd/codegen/mex/predictDigitECOC, где pwd является текущим рабочим каталогом. В дочернем каталоге codegen генерирует, среди прочего, MEX-файл predictDigitECOC_mex.mexw64.
Убедитесь, что файл MEX возвращает те же метки, что и predict.
mexLabels = predictDigitECOC_mex(testImages); verifyMEX = isequal(mexLabels,testLabels)
verifyMEX = logical
1
isequal возвращает логический 1 (true), что означает, что MEX-файл дает ожидаемые результаты.
loadLearnerForCoder | predict | saveLearnerForCoder | codegen (кодер MATLAB)