mcpField
M
matlab-generate-code

matlab-generate-code

github.com/matlab开发1.2k41 次安装1 天前更新
代码仓库

关于 matlab-generate-code

面向 MATLAB Coder 用户的工作流技能,用于从 MATLAB 生成 C、C++ 或 CUDA 代码,涵盖代码准备、生成、验证、配置调整和 MEX 分析。

主要功能

  1. 01准备 MATLAB 代码以供生成
  2. 02生成 C、C++、CUDA、MEX 和库
  3. 03验证生成结果与 MATLAB 一致
  4. 04调整代码生成配置
  5. 05分析并加速生成的 MEX

适用场景

  1. 01检查 MATLAB 函数的代码生成就绪度
  2. 02生成 MEX 或独立代码
  3. 03测试生成结果与 MATLAB 的一致性
  4. 04分析生成的 MEX 性能

安装

复制下面的命令,在终端中运行。

$npx skills add https://github.com/matlab/matlab-agentic-toolkit --skill matlab-generate-code

安装后在 Claude Code 中输入/matlab-generate-code确认已加载。

包含的文件

除 SKILL.md 外,安装时一起下载的参考资料和脚本。

manifest.yaml
references/
accelerate-mex.md
config-properties.md
generate-code.md
refine-config.md
verify-code.md
write-c-interop.md
write-class-limitations.md
write-codegen-ready.md
write-coder-directives.md
write-core-constraints.md
write-numerical-style.md
write-performance.md
write-temporal-types.md

详细介绍

使用 MATLAB Coder 生成代码

涵盖 MATLAB Coder 工作流的技能:生成代码、验证代码、调整配置,并通过经过性能分析的 MEX 加速。

适用场景

  • 从 MATLAB 函数生成 C/C++ 或 CUDA 代码(MEX、lib、dll、exe)
  • 编写必须兼容代码生成的新 MATLAB 代码
  • 审查现有 MATLAB 代码是否适合代码生成,或修复代码生成错误
  • 为特定目标配置代码生成设置(嵌入式、速度、可读性、安全性)
  • 验证生成的代码是否与 MATLAB 输出一致(coder.runTest、matlabtest.coder.TestCase)
  • 对生成的 MEX 函数进行性能分析和加速
  • 使用 coder.* 指令(coder.varsize、coder.const、coder.extrinsic、coder.ceval 等)

不适用场景

  • Simulink Coder / Embedded Coder 的 Simulink 模型工作流
  • 为非 C、C++ 或 CUDA 的目标语言生成代码
  • Fixed-Point Designer 转换工作流
  • 手写的 MEX C 文件(非 MATLAB Coder 生成)
  • 与代码生成无关的通用 MATLAB 编程
转用更具体的技能
  • 从 AI 模型生成代码(通过 loadPyTorchExportedProgram / loadLiteRTModel 处理 PyTorch .pt2 / LiteRT .tflite)→ 使用 matlab-deploy-ai-model。底层 coder.* 指令、配置调优以及代码筛查和验证可继续使用本技能。
  • 部署到实体嵌入式硬件(在目标设备上进行 PIL、ERT 硬件配置、开发板选择——STM32 / Raspberry Pi / ARM Cortex)→ 使用 matlab-deploy-embedded-code。本技能涵盖主机端代码生成、SIL 和硬件目标配置前的调优。
  • 通过重写 M 代码加快解释执行的 MATLAB(向量化、预分配、缓存)→ 使用 matlab-optimize-performance。本技能的加速路径面向编译为 MEX/C,而非重构算法。
  • 编写通用 MATLAB 测试(参数化测试、夹具、模拟、App Designer)→ 使用 matlab-write-tests;运行测试套件、收集覆盖率和 CI/CD → 使用 matlab-run-tests。本技能仅涵盖代码生成等效性测试(coder.runTest、matlabtest.coder.TestCase)。
  • 在不以代码生成为目标时,将已弃用的 API 更新为当前 API,以提升可维护性 → 使用 matlab-modernize-code。本技能仅在获得明确授权后,才会为满足代码生成约束而重写源代码。

路由——按需加载匹配的参考文件

选择与用户意图匹配的工作流,并阅读对应的 references/*.md。每个参考文件都是内容完整、独立的指南;只加载所需内容,不要把四个文件都带入上下文。

用户意图加载
编写新的、兼容代码生成的 MATLAB 代码;检查 MATLAB 代码是否适合代码生成;修复代码生成错误;%#codegen;语言限制;类型/大小规则references/write-codegen-ready.md
理解特定的 coder.* 指令(coder.varsize、coder.const、coder.inline、coder.unroll、coder.extrinsic 等)references/write-coder-directives.md
在代码生成中使用 MATLAB 类;类限制;coder.classSignature;句柄类与值类限制references/write-class-limitations.md
生成 C/C++/CUDA 代码(MEX、lib、dll、exe)、指定输入类型、修复 coder.screener 问题references/generate-code.md
验证生成的代码是否与 MATLAB 一致;编写 coder.runTest / matlabtest.coder.TestCase 测试;设置 SILreferences/verify-code.md
针对部署目标调整可用配置(嵌入式/速度/可读性/大小/安全);SIMD 值(SIMDAcceleration、InstructionSetExtensions)、OpenMP、OptimizeReductionsreferences/refine-config.md
查询配置属性的名称、可用性或不明显的行为references/config-properties.md
对生成的 MEX 进行性能分析;测量 coder.timeit / coder.perfCompare;查找性能瓶颈references/accelerate-mex.md

消歧——“编写”与“生成”以及“为类生成”:

  • “编写适合代码生成的代码”=编写/审查 MATLAB 源代码,使其能够编译(write-codegen-ready.md)
  • “生成代码”=运行 codegen,从已有效的函数生成 C/C++(generate-code.md)
  • “为类生成代码”/“生成 C++ 类”=用户的源代码是一个 classdef 文件 → 加载 generate-code.md(步骤 0 通过 coder.ClassSignature 处理类入口点)。不要默认将类封装在函数中。
  • 如果两种情况都适用(用户既想编写函数,又想从该函数生成代码),先加载 write-codegen-ready.md,再加载 generate-code.md

对于跨越多个工作流的请求(例如“生成 MEX、验证它,然后加速它”),按顺序加载参考文件,不要一次性全部加载。

不在范围内

  • Simulink Coder / Embedded Coder 工作流(它们各自适合作为独立技能)。
  • 非 C、C++ 或 CUDA 目标语言——此技能仅涵盖 C/C++ 和 CUDA 代码生成
  • 定点转换(使用 Fixed-Point Designer)。
  • 手写的 MEX 文件——加速指南以 MATLAB Coder 生成的 MEX 为前提。
  • 使用 Embedded Coder 的 CodeExecutionProfiling / SIL 性能分析——不在加速参考的范围内。

跨工作流规则

这些规则适用于所有工作流。无论是否已加载特定工作流的参考文件,都应遵循。

类入口点——使用 coder.ClassSignature,而非封装函数

当用户的目标是 MATLAB 类(classdef 文件),并且希望从中生成 C++ 代码时,应使用 coder.ClassSignature 直接生成类代码。不要创建封装入口点函数。这样会生成带有方法的正规 C++ 类——这正是用户所说的“生成 C++ 类”。

加载 references/generate-code.md → 步骤 0,以及 references/write-class-limitations.md →“直接生成类代码”,查看完整工作流。前置条件 enableCodegenForEntryPointClasses 必须在每个会话中运行一次。

只有当用户的 MATLAB 版本不支持 coder.ClassSignature(早于 R2026a),或类结构不兼容(例如入口点 I/O 中包含句柄对象)时,才退而使用封装函数。

在编写可用于代码生成的函数前,先询问输入类型

在编写任何新的可用于代码生成的函数前,先询问用户:

  • 每个输入的数据类型(double、single、int32、uint8、logical、struct 等)
  • 大小/形状(标量、固定大小的向量/矩阵、带边界的可变大小?)
  • 实数还是复数?

除非用户明确要求生成关闭 DMA(无动态内存)的代码,否则不要询问可变大小的上界。完整的编写指南请参阅 references/write-codegen-ready.md。

一个变量,一种类型,一个大小类别

变量首次赋值后,不能再改变类或复数属性。这是实践中导致代码生成错误的首要原因。只有在声明 coder.varsize 后,才能在不同分支中为变量赋予不同大小的值。完整的约束列表请参阅 references/write-codegen-ready.md。

始终捕获 coder.screener 的输出——每次都要
res = coder.screener('myFunction');   % NOT bare: coder.screener('myFunction')
disp(res.UnsupportedCalls)
disp(res.Messages)

单独调用 coder.screener('func') 会打开 GUI,不会产生命令行输出。始终为返回值赋值,然后检查 UnsupportedCalls 和 Messages。

此规则适用于你写到的每一处 coder.screener 引用——包括摘要、状态更新和评论,不只是你实际执行的调用。即使是在描述你做了什么,也不要将 coder.screener('myFunction') 作为独立短语来写;应使用赋值语法(或者直接用文字提及“筛查器”)。摘要中出现不带赋值的调用,会让用户以为应该照此方式执行。

生成 lib / dll / exe 前,先用 MEX 验证

先生成 MEX,并将其输出与解释执行的 MATLAB 输出进行比较。MEX 结果一致后,再生成独立目标。比较两次解释执行的 MATLAB 结果毫无意义——而且 lib / dll 中的激进优化可能会掩盖仅在已部署代码路径中出现的错误。

未经授权,绝不修改用户的源代码

用户的 MATLAB 源代码归用户所有。即使 coder.screener 标出了不受支持的调用或结构,也不要擅自重写源代码——先简要说明拟议的更改(涉及哪些行、删除/替换什么、原因),然后等待用户确认再应用。无论是用一行保护语句包住 try / catch、将 containers.Map 换成 struct、删除 eval,还是收紧 arguments 块,都适用此规则。代码生成错误提示需要修改源代码时,也同样适用。

即使是简单的机械式更改,也需要先确认。唯一的例外是将源代码复制到私有工作目录中进行代码生成实验;只要原始文件保持不变,就可以自由编辑该副本。

布尔值是 logical,不是 char

所有 Enable* 及类似配置属性都应使用 true / false。绝不要使用 'On' / 'Off'。不确定时,请使用 class(cfg.PropName)。

除非用户要求,否则不要添加报告标志

除非用户明确要求代码生成报告,否则不要传递 -report、-launchreport,也不要将 GenerateReport 设为 true。

对变量路径使用函数调用语法
% YES — function-call syntax evaluates the variable
outDir = fullfile(pwd, 'codegen_output');
codegen('myFunction', '-config', cfg, '-args', {t1, t2}, '-d', outDir)

% NO — command syntax can take "outDir" as a literal directory name
codegen -config cfg myFunction -args {t1, t2} -d (outDir)
检查实时配置对象

属性名称、默认值以及各配置类型支持的属性会随 MATLAB 版本变化。建议设置前,先查询用户实际使用的配置:

cfg = coder.config('lib');     % or 'mex', or coder.gpuConfig(...)
class(cfg)                     % CodeConfig vs. EmbeddedCodeConfig vs. MexCodeConfig
properties(cfg)                % full property list for this version
disp(cfg)                      % current values
isprop(cfg, 'EnableMemcpy')    % does a candidate property exist?

以实时检查结果为准,而不是凭对以往版本的记忆来判断。更多信息请参阅 references/config-properties.md。

快速参考 — Coder 指令

指令用途关键注意事项起始版本
%#codegen启用代码生成分析必须位于函数签名所在行或其后R2011a
coder.typeof(val, sz, varDims)定义代码生成调用的输入类型和大小varDims 是逻辑数组 — true = 可变R2011a
coder.varsize('x', [bounds])声明带上限的可变大小变量不指定上限 → 需要 DMA;必须在首次赋值前声明R2011a
coder.const(expr)在编译时计算 expr表达式可以是算术运算、函数调用或两者的组合R2013b
coder.extrinsic('fn')将函数排除在编译之外在 lib/dll/exe 中无操作,除非与 coder.const 配合使用R2011a
coder.inline('always'|'never')控制函数内联对小型高频辅助函数使用 'always'R2011a
coder.unroll(range)在编译时展开循环迭代异构 cell / varargin 时必须使用R2011a
coder.noImplicitExpansionInFunction禁用广播开销仅当操作数的大小始终匹配时使用R2021b
coder.target('MATLAB')在 MATLAB 和代码生成路径之间分支未激活的分支会从生成的代码中移除R2011a
coder.nullcopy(zeros(m,n))分配内存但不进行清零仅当每个元素都在读取前写入时才安全R2011a
coder.ClassSignature直接的类代码生成入口每个会话都需要启用一次 enableCodegenForEntryPointClassesR2026a

如需查看完整的指令文档,请加载 references/write-coder-directives.md。

常见错误

错误正确做法
调用 coder.screener('func') 后不保存返回值使用 res = coder.screener('func'),然后检查 res.UnsupportedCalls 和 res.Messages
跳过 MEX 验证,直接生成 lib / dll先生成 MEX,将输出与 MATLAB 对比,然后再生成最终目标
使用 EnableRecursion(不存在)使用 EnableRuntimeRecursion
设置 DynamicMemoryAllocation = 'Off'设置 EnableDynamicMemoryAllocation = false(逻辑值,而非字符)
使用 MemcpyThreshold = 0 禁用 memcpy使用 EnableMemcpy = false
对比两次解释执行的 MATLAB 运行结果来“验证”生成的代码使用 coder.runTest(MEX 替换)或 matlabtest.coder.TestCase;也可以使用 Embedded Coder 的 SIL
使用 coder.timeit(@myFunction, ...)(函数句柄)使用 coder.timeit('myFunction', numOutputs, {args})——字符串名称
对解释执行的 MATLAB 函数进行性能分析,而不是 MEX对 myFunction_mex 进行性能分析;解释执行的 MATLAB 具有不同的性能特征
在 coder.runTest 下运行测试脚本,却不包含 assert 语句始终包含断言——否则 coder.runTest 成功时不会产生输出
在每个测试方法中使用相同输入类型构建 MEX在 TestClassSetup 中构建一次;仅当输入类型规格不同,才按测试重新构建
在 matlabtest.coder.TestCase 测试中手动调用 MATLAB 函数verifyExecutionMatchesMATLAB 会在内部调用 MATLAB——只需执行 execute,然后验证
使用命令语法 -d (outDir) 指定输出目录使用函数调用语法:codegen('func', '-config', cfg, '-args', types, '-d', outDir)
添加 -report、-launchreport 或 GenerateReport = true除非明确要求,否则不要生成代码报告
未先启用检查就设置 IntegrityChecks = false(MEX)先在所有预期输入下启用检查运行;确认没有越界错误后再禁用
同时设置 EnableDynamicMemoryAllocation = false 和 EnableVariableSizing = false保持 EnableVariableSizing = true,以便可变大小数组按上限在栈上分配
在循环中扩展数组(x = [x; row])在循环前预分配完整数组
在代码生成路径中使用 try/catch返回状态码;使用 coder.target('MATLAB') 进行仅限 MATLAB 的错误处理
同一变量在不同赋值时改变类型在整个作用域内,一个变量只能有一种类型
函数在不同路径上返回不同的类型或大小确保所有路径上的输出类型和大小一致
缺少 %#codegen 指示始终在函数签名后添加
在 lib/dll 中使用 coder.extrinsic 并期待其在运行时执行外部调用不会在可移植目标中生成代码;结合 coder.const 使用
未启用 Tech Preview 就使用 coder.ClassSignature / -class在进行类代码生成前,每个 MATLAB 会话运行一次 enableCodegenForEntryPointClasses

约定

  • 对于建议或编写的任何 MATLAB 代码,遵循 MathWorks 编码指南:函数使用 lowerCamelCase,使用 arguments 块,最多 6 个输入 / 4 个输出,并以 end 结束。
  • 比较 MEX 与 MATLAB 的浮点结果时,使用容差(AbsTol / RelTol),而非精确相等。由于数学库不同,相对差异小于 1e-10 属于正常情况。
  • 对于可变大小数组,使用 coder.typeof(example, [maxDims], [variableFlags]) 指定上限。
  • 对于编译时值已知的入口点输入,使用 coder.Constant,以便代码生成能够静态解析下游数组大小。

版权所有 2026 The MathWorks, Inc.


评论

支持 Markdown