可变大小数据是指其大小在运行时可能改变的数据。您可以使用MATLAB®编码器™从MATLAB代码生成C/ c++代码,使用可变大小的数据。MATLAB支万博1manbetx持有界和无界变量大小的数据用于代码生成。有界可变大小数据有固定的上界。这个数据可以在堆栈上静态分配,也可以在堆上动态分配。无界适应数据没有固定的上界。这个数据必须分配到堆上。默认情况下,对于MEX和C/ c++代码生成,启用了对可变大小数据的支持,并为大小大于或等于可万博1manbetx配置阈值的可变大小数组启用了动态内存分配。
默认情况下,对于MEX和C/ c++代码生成,启用了对可变大小数据的支持。万博1manbetx您可以从项目设置对话框、命令行或使用对话框中修改可变大小设置。
打开生成对话框,位于生成代码页面,点击生成箭头.
点击更多的设置.
在内存选项卡,选择或清除启用可变大小.
创建用于代码生成的配置对象。例如,对于库:
cfg = coder.config(“自由”);
设定启用可变大小
选项:
cfg。EnableVariableSizing = false;
使用配置
选项,将配置对象传递给codegen
:
codegen-config cfg foo
默认情况下,对大小大于或等于可配置阈值的可变大小数组启用动态内存分配。如果您禁用了对可变大小数据的支万博1manbetx持(参见禁用支持可变大小万博1manbetx数据),您还可以禁用动态内存分配。可以从“项目设置”对话框或命令行修改动态内存分配设置。
打开生成对话框,位于生成代码页面,点击生成箭头.
点击更多的设置.
在内存选项卡,设置动态内存分配选择下列选项之一:
背景 | 行动 |
---|---|
从来没有 |
禁用动态内存分配。可变大小的数据是在堆栈上静态分配的。 |
对于所有可变大小的阵列 |
为可变大小的数组启用了动态内存分配。在堆上动态分配大小可变的数据。 |
对于最大大小等于或高于阈值的阵列 |
的大小为可变大小的数组启用动态内存分配动态内存分配阈值.在堆栈上分配大小小于此阈值的可变大小数组。 |
如果你设置动态内存分配来对于最大大小大于或等于阈值的数组
,配置动态内存分配阈值调整内存分配。
创建用于代码生成的配置对象。例如,对于MEX函数:
mexcfg = coder.config(墨西哥人);
设定动态内存分配
选项:
背景 | 行动 |
---|---|
mexcfg.DynamicMemoryAllocation =“关闭”; |
禁用动态内存分配。可变大小的数据是在堆栈上静态分配的。 |
mexcfg.DynamicMemoryAllocation =“AllVariableSizeArrays”; |
为可变大小的数组启用了动态内存分配。在堆上动态分配大小可变的数据。 |
mexcfg.DynamicMemoryAllocation =“阈值”; |
属性指定的大小(以字节为单位)大于或等于可变大小数组的值时,将启用动态内存分配DynamicMemoryAllocationThreshold 参数。在堆栈上分配大小小于此阈值的可变大小数组。 |
如果你设置动态内存分配
来“阈值”
,配置DynamicMemoryAllocationThreshold
微调内存分配。
使用配置
选项,将配置对象传递给codegen
:
Codegen -config mexcfg foo
下面是一个基本的工作流,它首先生成MEX代码以验证生成的代码,然后在您对原型的结果感到满意后生成独立的代码。
要通过一个简单的示例完成这些步骤,请参见为循环中展开向量的MATLAB函数生成代码
在MATLAB编辑器中,添加编译指令% # codegen
在你的功能的顶端。
这个指令:
表示您打算为MATLAB算法生成代码
打开MATLAB代码分析器中的检查,以检测代码生成期间的潜在错误
解决代码分析器检测到的问题。
在某些情况下,当代码为数据指定了固定大小,但随后又增加了数据时(例如通过循环中的指定或串联),MATLAB代码分析器会发出警告。如果该数据在运行时大小不同,则可以忽略这些警告。
使用codegen
以验证生成的代码。使用以下命令行选项:
args {coder.typeof…}
如果你有可变大小的输入
-报告
生成代码生成报告的步骤
例如:
Codegen -report foo -args{编码器。typeof (0, 2 [4], 1)}
coder.typeof
为函数指定一个可变大小输入的步骤喷火
. 第一个论点,,0
,表示输入数据类型(双重的
)和复杂性(真正的
).第二个参数,(2 - 4)
,表示大小,一个二维矩阵。第三个参数,1
,表示输入是可变大小的。第一维的上限是2,第二维的上限是4。
请注意
在编译过程中,codegen
检测在定义变量和结构字段后大小发生变化的变量和结构字段,并将这些情况报告为错误。此外,codegen
当数据超过上限时,执行运行时检查以生成错误。
修复尺寸不匹配错误:
原因 | 如何修复 | 的更多信息 |
---|---|---|
锁定数据大小后,尝试更改其大小。 | 声明数据为可变大小。 | 看到诊断和修复大小不匹配错误. |
修正上界错误
原因 | 如何修复 | 的更多信息 |
---|---|---|
MATLAB无法确定或计算上限 | 请指定上限。 | 看到指定可变大小数组的上界和诊断和修复大小不匹配错误. |
MATLAB试图计算无界可变大小数据的上限。 | 如果数据是无界的,请启用动态内存分配。 | 看到控制动态内存分配. |
生成C/ c++代码使用codegen
函数。
此示例使用函数米尼克托
.这个函数以vector形式返回B
输入向量的一个版本一个
,其中元素在公差范围内是唯一的托尔
彼此的。在向量B
,腹肌
(B
(我
)- - -B
(j
)) >托尔
对所有我
和j
.首先,假设输入向量一个
可存储多达100个元素。
函数B=myuniquetol(A,tol)A=sort(A);B=A(1);k=1;为我= 2:长度(A)如果abs(A(k) - A(i)) > tol B = [B A(i)];k =我;结束结束
添加% # codegen
函数顶部的编译指令:
函数B = myuniquetol(A, tol)% # codegen一种=(一个);B = (1);k = 1;为我= 2:长度(A)如果abs(A(k) - A(i)) > tol B = [B A(i)];k =我;结束结束
代码分析器检测该变量B
可能会改变大小对- - - - - -
环它发出以下警告:
变量'B'似乎在每次循环迭代时都会改变大小。考虑提前分配。
在这个函数中,你期望向量B
扩展大小,因为它从向量中添加值一个
。因此,您可以忽略此警告。
最佳做法是在生成C/C++代码之前生成MEX代码。生成MEX代码可以识别在运行时更难检测的代码生成问题。
为生成一个MEX函数米尼克托
:
Codegen -report myuniquetol -args{编码器。typeof (0, [100], 1), coder.typeof (0)}
代码生成成功。codegen
不检测问题。在当前文件夹中,codegen
为生成一个MEX函数米尼克托
并提供到代码生成报告的链接。
点击查看报告链接。
在“代码生成”报告中,选择变量标签。
的大小一个
是1 x: 100
因为你指定了一个
是上限为的可变大小One hundred.
.变量的大小B
是1x:?
,表示它是没有上限的可变大小。
为可变大小的输入生成C代码。默认情况下,codegen
为小于动态内存分配阈值64kb的数据静态分配内存。如果数据的大小大于或等于阈值或无边界,codegen
在堆上动态分配内存。
为C库生成创建一个配置选项:
cfg = coder.config(“自由”);
发出此命令:
Codegen -config CFG -report myuniquetol -args{编码器。typeof (0, [100], 1), coder.typeof (0)}
codegen
在默认位置生成静态库,codegen \ lib \ myuniquetol
并提供到代码生成报告的链接。
点击查看报告链接。
在生成的文件列表中,单击米尼克托
.
函数声明是:
extern void myuniquetol(const double A_data[], const int A_size[2], double tol, emxArray_real_T *B);
codegen
计算对象的大小一个
而且,因为它的最大大小小于默认的动态内存分配阈值64k字节,所以静态分配该内存。生成的代码包含:
双A_data []
:定义一个
.
int A_size [2]
:输入的实际大小。
代码生成器确定B
具有未知上界的可变大小。它代表了B
作为emxArray_real_T
.MATLAB提供了用于创建和交互的实用函数emxArrays
在您生成的代码中。有关更多信息,请参见在生成的函数接口中使用C数组.
您指定输入一个
是上限为的可变大小One hundred.
. 因此,您知道输出B
不能大于One hundred.
元素。
使用变码器
表明B
是上限为的可变大小One hundred.
.
函数B = myuniquetol(A, tol) %#codegen A = sort(A);变码器('B', [1 100], [0 1]); B = A(1); k = 1; for i = 2:length(A) if abs(A(k) - A(i)) > tol B = [B A(i)]; k = i; end end
生成代码。
Codegen -config CFG -report myuniquetol -args{编码器。typeof (0, [100], 1), coder.typeof (0)}
函数声明是:
外部无效myuniquetol(常数双A_数据[],常数内A_大小[2],双tol,双B_数据[],内B_大小[2]);
代码生成器静态地为以下对象分配内存B
.它存储的大小B
在int B_size [2]
.
在这一步中,您将降低动态内存分配阈值,并为超过该阈值的输入生成代码。此步骤指定的第二个维度一个
的上界是10000
.
改变的上界B
的上界一个
.
函数B = myuniquetol(A, tol) %#codegen A = sort(A);变码器('B', [1 10000], [0 1]); B = A(1); k = 1; for i = 2:length(A) if abs(A(k) - A(i)) > tol B = [B A(i)]; k = i; end end
将动态内存分配阈值设置为4 KB,并生成输入大小为一个
超过这个阈值。
cfg.DynamicMemoryAllocationThreshold = 4096;Codegen -config CFG -report myuniquetol -args{编码器。typeof (0, [10000], 1), coder.typeof (0)}
在报告中查看生成的代码。因为最大的尺寸一个
和B
现在超过了动态内存分配阈值,codegen
分配一个
和B
动态地在堆上。在生成的代码中,一个
和B
有类型emxArray_real_T
.
外部无效myuniquetol(常数emxArray_real_T*A、双tol、emxArray_real_T*B);