Unrolling for
-loops eliminates the loop logic
by creating a separate copy of the loop body in the generated code
for each iteration. Within each iteration, the loop index variable
becomes a constant.
You can also force loop unrolling for individual functions by
wrapping the loop header in a coder.unroll
function.
For more information, see coder.unroll
.
for
-loop Body in Generated CodeTo limit the number of times that you copy the body of a for-
loop
in generated code:
Write a MATLAB® function getrand(n)
that
uses a for-
loop to generate a vector of length n
and
assign random numbers to specific elements. Add a test function test_unroll
.
This function calls getrand(n)
with n
equal
to values both less than and greater than the threshold for copying
the for-
loop in generated code.
function [y1, y2] = test_unroll() %#codegen % The directive %#codegen indicates that the function % is intended for code generation % Calling getrand 8 times triggers unroll y1 = getrand(8); % Calling getrand 50 times does not trigger unroll y2 = getrand(50); function y = getrand(n) % Turn off inlining to make % generated code easier to read coder.inline('never'); % Set flag variable dounroll to repeat loop body % only for fewer than 10 iterations dounroll = n < 10; % Declare size, class, and complexity % of variable y by assignment y = zeros(n, 1); % Loop body begins for i = coder.unroll(1:2:n, dounroll) if (i > 2) && (i < n-2) y(i) = rand(); end; end; % Loop body ends
Disable support for
In the default output folder, codegen/lib/test_unroll
,
generate C static library code for test_unroll
:
codegen -config:lib test_unroll
In test_unroll.c
, the generated C code for getrand(8)
repeats
the body of the for-
loop (unrolls the loop) because
the number of iterations is less than 10:
static void getrand(double y[8]) { /* Turn off inlining to make */ /* generated code easier to read */ /* Set flag variable dounroll to repeat loop body */ /* only for fewer than 10 iterations */ /* Declare size, class, and complexity */ /* of variable y by assignment */ memset(&y[0], 0, sizeof(double) << 3); /* Loop body begins */ y[2] = b_rand(); y[4] = b_rand(); /* Loop body ends */ }
The generated C code for getrand(50)
does
not unroll the for-
loop because the number of iterations
is greater than 10:
static void b_getrand(double y[50]) { int i; int b_i; /* Turn off inlining to make */ /* generated code easier to read */ /* Set flag variable dounroll to repeat loop body */ /* only for fewer than 10 iterations */ /* Declare size, class, and complexity */ /* of variable y by assignment */ memset(&y[0], 0, 50U * sizeof(double)); /* Loop body begins */ for (i = 0; i < 25; i++) { b_i = (i << 1) + 1; if ((b_i > 2) && (b_i < 48)) { y[b_i - 1] = b_rand(); } }