Ускорьте Код Используя fiaccel

Ускорение Выполнения Фиксированной точки с fiaccel

Можно преобразовать фиксированную точку код MATLAB® в MEX-функции с помощью fiaccel. Сгенерированные MEX-функции содержат оптимизацию, чтобы автоматически ускорить алгоритмы фиксированной точки к скомпилированной скорости C/C++ кода в MATLAB. Функция fiaccel может значительно увеличить скорость выполнения ваших алгоритмов.

Выполнение fiaccel

Основная команда:

fiaccel M_fcn

По умолчанию fiaccel выполняет следующие действия:

  • Поиски функционального M_fcn сохранили в файле M_fcn.m, как задано в Порядке Поиска Пути к Компиляции.

  • Компиляции M_fcn к коду MEX.

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

  • Если существуют ошибки, не генерирует файл MEX, но производит сообщение об ошибке в выходной папке по умолчанию, как описано в Сгенерированных Файлах и Местоположениях.

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

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

Сгенерированные файлы и местоположения

fiaccel генерирует файлы в следующих местоположениях:

Генерирует:\in:

Специфичные для платформы файлы MEX

Текущая папка

генерация кода сообщает

(если ошибки или предупреждения происходят во время компиляции),

Выходная папка по умолчанию:

fiaccel/mex/M_fcn_name/html

Можно изменить название и местоположение сгенерированных файлов при помощи опций -o и -d, когда вы запускаете fiaccel.

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

Сравнение времени выполнения при ускорении различных частей алгоритма

Алгоритм, используемый в этом примере, реплицирует функциональность функции sum MATLAB, которая суммирует столбцы матрицы. Чтобы видеть алгоритм, введите open fi_matrix_column_sum.m в командной строке MATLAB.

function B = fi_matrix_column_sum(A)
% Sum the columns of matrix A.
%#codegen
    [m,n] = size(A);
    w = get(A,'WordLength') + ceil(log2(m));
    f = get(A,'FractionLength');
    B = fi(zeros(1,n),true,w,f);
    for j = 1:n
        for i = 1:m
            B(j) = B(j) + A(i,j);
        end
    end

Испытание 1: лучшая производительность

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

Первый фрагмент кода выполняет алгоритм с помощью только функции MATLAB. Второй фрагмент кода компилирует целый алгоритм с помощью функции fiaccel. tic MATLAB и функции toc отслеживают время выполнения для каждого метода выполнения.

% MATLAB
fipref('NumericTypeDisplay','short');
A = fi(randn(1000,10));
tic
B = fi_matrix_column_sum(A)
t_matrix_column_sum_m = toc

% fiaccel
fiaccel fi_matrix_column_sum -args {A} ...
-I [matlabroot '/toolbox/fixedpoint/fidemos']
tic
B = fi_matrix_column_sum_mex(A);
t_matrix_column_sum_mex = toc

Испытание 2: худшая производительность

Компиляция только самого маленького модуля вычисления с помощью функции fiaccel приводит к намного более медленному выполнению. В некоторых случаях издержки, которые следуют из вызывания функции mex во вложенном цикле, могут вызвать еще более медленное выполнение, чем использование одних только функций MATLAB. Чтобы оценить производительность функции mex, когда только самый маленький модуль вычисления будет скомпилирован, запустите следующий код.

Первый фрагмент кода выполняет алгоритм с помощью только функции MATLAB. Второй фрагмент кода компилирует самый маленький модуль вычисления с функцией fiaccel, оставляя остальную часть вычислений MATLAB.

% MATLAB
tic
[m,n] = size(A);
w = get(A,'WordLength') + ceil(log2(m));
f = get(A,'FractionLength');
B = fi(zeros(1,n),true,w,f);
for j = 1:n
    for i = 1:m
        B(j) = fi_scalar_sum(B(j),A(i,j));
        % B(j) = B(j) + A(i,j);
    end
end
t_scalar_sum_m = toc

% fiaccel
fiaccel fi_scalar_sum -args {B(1),A(1,1)} ...
-I [matlabroot '/toolbox/fixedpoint/fidemos']
tic
[m,n] = size(A);
w = get(A,'WordLength') + ceil(log2(m));
f = get(A,'FractionLength');
B = fi(zeros(1,n),true,w,f);
for j = 1:n
    for i = 1:m
        B(j) = fi_scalar_sum_mex(B(j),A(i,j));
        % B(j) = B(j) + A(i,j);
    end
end
t_scalar_sum_mex = toc

Отношение времен

Сравнение Испытания 1 и Испытания 2 появляется в следующей таблице. Ваш компьютер может записать различные времена, чем те, таблица показывает, но отношения должны быть приблизительно тем же самым. Существует экстремальное различие в отношениях между испытанием, где целый алгоритм был скомпилирован с помощью fiaccel (t_matrix_column_sum_mex.m) и где только скалярная сумма была скомпилирована (t_scalar_sum_mex.m). Даже файл без компиляции fiaccel (t_matrix_column_sum_m) добился большего успеха чем тогда, когда только самый маленький модуль вычисления был скомпилирован с помощью fiaccel (t_scalar_sum_mex).

X (ранг общей производительности)ВремяX/BestX_m/X_mex
Испытание 1: лучшая производительность
t_matrix_column_sum_m (2) 1.99759 84.4917 84.4917
t_matrix_column_sum_mex (1)0.02364241
Испытание 2: худшая производительность
t_scalar_sum_m (4)10.2067 431.71 2.08017
t_scalar_sum_mex (3)4.90664 207.536

Переопределение Типа данных Используя fiaccel

Программное обеспечение Fixed-Point Designer™ поставляется с примером того, как сгенерировать MEX-функцию из кода MATLAB. Код в примере берет взвешенное среднее сигнала создать фильтр lowpass. Чтобы запустить пример в Браузере документации выбирают MATLAB Examples под Fixed-Point Designer, и затем выбирают Fixed-Point Lowpass Filtering Using MATLAB for Code Generation.

Можно задать переопределение типа данных в этом примере путем ввода дополнительной команды в посдказке MATLAB в разделе “Define Fixed-Point Parameters” примера. Чтобы включить переопределение типа данных, введите следующую команду в посдказке MATLAB после выполнения команды reset(fipref) в том разделе:

fipref('DataTypeOverride','TrueDoubles')

Эта команда говорит программному обеспечению Fixed-Point Designer создавать все объекты fi с типом fi double. Когда вы компилируете код с помощью команды fiaccel в разделе “Compile the M-File into a MEX File” примера, получившаяся MEX-функция использует данные с плавающей точкой.

Определение Значения по умолчанию fimath Значения для MEX-функций

MEX-функции, сгенерированные с fiaccel, используют значение по умолчанию MATLAB глобальный fimath. Глобальная переменная заводской настройки MATLAB fimath имеет следующие свойства:

RoundingMethod: Nearest
OverflowAction: Saturate
ProductMode: FullPrecision
SumMode: FullPrecision

При выполнении MEX-функций, которые зависят от значения по умолчанию MATLAB значение fimath, не изменяйте это значение во время сеанса работы с MATLAB. В противном случае MATLAB генерирует предупреждение, предупреждая вас к несоответствию между временем компиляции и значениями fimath во время выполнения. Например, создайте следующую функцию MATLAB:

function y = test %#codegen 
y = fi(0); 
Функциональный test создает объект fi, явным образом не задавая объект fimath. Поэтому test полагается на объект fimath по умолчанию в действительности во время компиляции.

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

resetglobalfimath;
fiaccel test 
fiaccel генерирует MEX-функцию, test_mex, в текущей папке.

Запустите test_mex.

test_mex   
ans =        
  0            
       DataTypeMode: Fixed-point: binary point scaling            
       Signedness: Signed            
       WordLength: 16        
       FractionLength: 15

Измените значение по умолчанию MATLAB значение fimath, таким образом, это больше не совпадает с установкой, используемой во время компиляции.

F = fimath('RoundingMethod','Floor');
globalfimath(F); 

Очистите MEX-функцию из памяти и повторно выполните его.

clear test_mex 
test_mex
Несоответствие обнаруживается, и MATLAB генерирует предупреждение.
testglobalfimath_mex 
Warning: This function was generated with a different default fimath than the current default.   
ans =        
   0            
      DataTypeMode: Fixed-point: binary point scaling            
      Signedness: Signed             
      WordLength: 16         
      FractionLength: 15
Чтобы избежать этой проблемы, разделите свойства fimath от своего алгоритма при помощи таблиц типов. Для получения дополнительной информации смотрите Отдельные Определения типов из Алгоритма.