Модульный тест внешний код С с MATLAB CODER

Этот пример показывает, как протестировать внешний код С при помощи модульных тестов MATLAB® с MATLAB® Coder™.

Если вы хотите протестировать код С, можно использовать MATLAB CODER, чтобы принести код в MATLAB. Можно затем записать модульные тесты при помощи среды тестирования MATLAB. Можно записать более богатые, более гибкие тесты путем использования в своих интересах усовершенствованных числовых возможностей вычисления и визуализации MATLAB.

Этот пример показывает как:

  1. Принесите свой код С в MATLAB как MEX-функция, которую вы генерируете с MATLAB CODER.

  2. Запишите модульный тест при помощи среды тестирования MATLAB.

  3. Запустите тест на MEX-функции.

Если вы Встроили Coder®, можно запустить модульные тесты на сгенерированном автономном коде (статическая библиотека или совместно использованная библиотека) при помощи модульных тестов с программным обеспечением в цикле (SIL) выполнение или процессор в цикле (PIL) выполнение.

Исследуйте файлы

Чтобы получить доступ к файлам, которые использует этот пример, нажмите Open Script.

kalmanfilter. c

kalmanfilter.c является функцией C, которую тестирует пример. Это оценивает положение перемещения, основанного на объектах на его прошлых положениях.

kalmanfilter. h

kalmanfilter.h является заголовочным файлом для kalmanfilter.c c.

position.mat

position.mat содержит положения объекта.

callKalmanFilter. m

callKalmanFilter вызывает kalmanfilter при помощи coder.ceval.

function [a,b] = callKalmanFilter(position)
% Copyright 2014 - 2016 The MathWorks, Inc.

numPts = size(position,2);

a = zeros(2,numPts,'double');
b = zeros(2,numPts,'double');
y = zeros(2,1,'double');

% Main loop
for idx = 1: numPts
    z = position(:,idx);     % Get the input data
    
    % Call the initialize function
    coder.ceval('kalmanfilter_initialize');
    
    % Call the C function
    coder.ceval('kalmanfilter',z,coder.ref(y));
    
    % Call the terminate function
    coder.ceval('kalmanfilter_terminate');
    
    a(:,idx) = [z(1); z(2)];
    b(:,idx) = [y(1); y(2)];
end
end

TestKalmanFilter. m

TestKalmanFilter тестирует, превышает ли ошибка между предсказанным положением и фактическим положением заданный допуск. Модульные тесты являются модульными тестами, основанными на классах. Для получения дополнительной информации смотрите Создание модульных тестов на основе классов в MATLAB (MATLAB).

Несмотря на то, что вы хотите протестировать MEX-функцию, модульные тесты в TestKalmanFilter вызывают исходную функцию MATLAB, от которой вы сгенерировали MEX-функцию. Когда MATLAB CODER запускает тесты, он заменяет вызовы функции MATLAB с вызовами MEX-функции. Вы не можете запустить эти тесты непосредственно в MATLAB, потому что MATLAB не распознает вызовы coder.ceval в callKalmanFilter.

classdef TestKalmanFilter < matlab.unittest.TestCase
    % Copyright 2014 - 2016 The MathWorks, Inc.
    
    methods ( Test )
        
        function SSE_LessThanTolerance( testCase )
            load position.mat;
            [z,y] = callKalmanFilter( position );
            
            tolerance = 0.001; % tolerance of 0.0001 will break
            A = z-1000*y;
            error = sum(sum(A.^2));
            
            testCase.verifyLessThanOrEqual( error, tolerance);
            
            % For debugging
            plot_kalman_filter_trajectory(z,1000*y);
        end
        
        function SampleErrorLessThanTolerance( testCase )
            load position.mat;
            [z,y] = callKalmanFilter( position );
            
            tolerance = 0.01;   % tolerance of 0.001 will break
            A = z-1000*y;

            testCase.verifyEqual(1000*y, z, 'AbsTol', tolerance);
            % For debugging
            plot_kalman_filter_trajectory(z,1000*y);
            
            [value, location] = max(A(:));
            [R,C] = ind2sub(size(A),location);
            disp(['Max value ' num2str(value) ' is located at [' num2str(R) ',' num2str(C) ']']);
        end
    end
end

run_unit_tests_kalman. m

run_unit_tests_kalman вызывает runtests, чтобы запустить тесты в TestKalmanFilter.m m.

% Run unit tests
% Copyright 2014 - 2016 The MathWorks, Inc.

runtests('TestKalmanFilter')

plot_kalman_filter_trajectory. m

plot_kalman_filter_trajectory строит график траектории предполагаемых и фактических положений объекта. Каждый модульный тест вызывает эту функцию.

Сгенерируйте MEX и запущенные модульные тесты в приложении MATLAB CODER

Чтобы открыть приложение MATLAB CODER, на вкладке MATLAB Toolstrip Apps, под Генерацией кода, кликают по значку приложения MATLAB CODER.

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

  • На странице Select Source Files укажите, что функцией точки входа является callKalmanFilter.

  • На странице Define Input Types укажите, что входной параметр, из которого x 2 310 массив, удваивается.

Модульные тесты загружают переменный position от position.mat и передают position callKalmanFilter. Поэтому входной параметр к callKalmanFilter должен иметь свойства, которые имеет position. В MATLAB workspace, если вы загружаете position.mat, вы видите, что position 2 310, массив удваивается.

  • Пропустите Проверку на шаг Проблем Во время выполнения для этого примера.

Сконфигурируйте приложение для генерации кода MEX. Задайте имена исходных и заголовочных файлов C, потому что callKalmanFilter интегрирует внешний код С.

  1. Для типа Сборки задайте MEX.

  2. Нажмите More Settings.

  3. На вкладке Custom Code:

  • Под Пользовательским кодом С для Сгенерированных Файлов выберите Заголовочный файл. В поле пользовательского кода введите #include "kalmanfilter.h" h.

  • В Дополнительном поле исходных файлов введите kalmanfilter.c c.

Чтобы сгенерировать MEX-функцию, нажмите Generate.

Запустите модульные тесты на сгенерированном MEX.

  1. Нажмите Verify Code.

  2. В поле для тестового файла задайте run_unit_tests_kalman.

  3. Убедитесь, что вы устанавливаете использование Выполнения на Сгенерированный код.

  4. Нажмите Run Generated Code.

Когда выполнение приложения тестовый файл, это заменяет вызовы callKalmanFilter в модульном тесте с вызовами callKalmanFilter_mex. Модульные тесты работают на MEX-функции вместо исходной функции MATLAB.

Отображения приложения тест выводятся на вкладке Test Output. Передача модульных тестов.

Из графиков вы видите, что траектория предполагаемого положения сходится с траекторией фактического положения.

Запустите модульные тесты после изменения кода С

Когда вы изменяете код С, чтобы запустить модульные тесты:

  1. Регенерируйте MEX-функцию для функции MATLAB, которая вызывает код С.

  2. Повторите шаг верификации.

Например, измените kalmanfilter.c так, чтобы значение, присвоенное y[r2], было умножено на 1,1.

y[r2] += (double)d_a[r2 + (i0 << 1)] * x_est[i0] * 1.1;

Отредактируйте kalmanfilter.c за пределами приложения, потому что можно использовать приложение, чтобы отредактировать только файлы MATLAB, перечисленные в панели Исходного кода приложения.

Чтобы сгенерировать MEX-функцию для измененной функции, нажмите Generate.

Запускать модульные тесты:

  1. Нажмите Verify Code.

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

  3. Нажмите Run Generated Code.

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

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

Сгенерируйте MEX и запущенные модульные тесты при помощи рабочего процесса командной строки

Можно использовать рабочий процесс командной строки, чтобы запустить модульные тесты на внешнем коде С при помощи coder.runTest runTest. Задайте тестовый файл, который запускает модульные тесты на функции MATLAB, которая вызывает ваш код С.

Сгенерируйте MEX-функцию для функции MATLAB, которая вызывает ваш код С. Для этого примера сгенерируйте MEX для callKalmanFilter.

Создайте объект настройки для генерации кода MEX.

cfg = coder.config('mex');

Задайте внешний исходный код и заголовочный файл.

cfg.CustomSource = 'kalmanfilter.c';
cfg.CustomHeaderCode = '#include "kalmanfilter.h"';

Чтобы определить тип для входного параметра к callKalmanFilter, загрузите файл положения.

load position.mat

Чтобы сгенерировать MEX-функцию, запустите codegen. Укажите, что входной параметр к callKalmanFilter имеет тот же тип как position.

codegen -config cfg callKalmanFilter -args position

Запустите модульные тесты на MEX-функции. Укажите, что тестовым файлом является run_unit_tests_kalman и что функцией является callKalmanfilter. Когда coder.runTest запускает тестовый файл, он заменяет вызовы callKalmanFilter в модульном тесте с вызовами callKalmanFilter_mex. Модульные тесты работают на MEX-функции вместо исходной функции MATLAB.

coder.runTest('run_unit_tests_kalman', 'callKalmanFilter')
Running TestKalmanFilter
Current plot held
.Current plot held
Max value 0.0010113 is located at [2,273]
.
Done TestKalmanFilter
__________


ans = 

  1x2 TestResult array with properties:

    Name
    Passed
    Failed
    Incomplete
    Duration
    Details

Totals:
   2 Passed, 0 Failed, 0 Incomplete.
   29.7256 seconds testing time.

Смотрите также

Похожие темы

Была ли эта тема полезной?