首页 最新 热门 推荐

  • 首页
  • 最新
  • 热门
  • 推荐

Matlab编程技巧:通过脚本写入C代码内容

  • 23-09-22 00:45
  • 2282
  • 7270
blog.csdn.net

本文介绍一种通过Matlab脚本写入C代码的方法,以实现通过管理表格文件就可以生成具有一定规律的C代码,从而减少人工手写代码的工作量。

文章目录

  • 1 问题引入
  • 2 需求示例
  • 3 示例脚本
  • 4 脚本说明
    • 4.1 step1 读取表格信息
    • 4.2 step2 将代码内容写入变量CodeText中
      • 4.2.1 头文件、函数名、定义结构体
      • 4.2.2 使能端口时钟
      • 4.2.3 端口配置
    • 4.3 step3 将变量CodeText写入led.c文件中
  • 5 总结

1 问题引入

在MBD中,并非所有的代码都适合通过Simulink模型生成。通常来说,会用Simulink模型搭建控制算法,然后将其生成代码。

而一些与配置相关的功能,则会通过人工手写C代码的方式完成。譬如EEPROM配置代码,CAN帧配置代码等,往往通过直接手写会比Simulink建模更加容易实现。

这种手写代码有几个特点:

  • 改动比较频繁。如果需求经常变,那么配置的代码就会经常变。
  • 具有一定规律。比方说很多EEPROM变量按照同种方式赋值给结构体,或者CAN信号按照某种规律装填到某一帧里面
  • 人工手写容易出错。代码看起来眼花缭乱,一不留神就会写错。

所以针对这些问题,博主比较喜欢通过Excel表格,把CAN、EEPROM这些变量的属性管理起来,然后通过脚本读取表格,自动写入C文件和头文件。每次需求变更的时候,只要更新好表格在运行脚本,那然后生成C文件只是一瞬间的事情。

2 需求示例

由于CAN、HWIO和EEPROM的代码在汽车软件团队中的保密级别比较高,所以就没法通过这些来举例了。博主打算通过比较常见的stm32f103的GPIO配置代码,来说明整个流程和思路。

熟悉stm32GPIO配置的博友肯定对下面的led.c的C代码不会陌生,因为这是经典的跑马灯实验中初始化LED灯的C代码。

#include  "led.h"

void LED_Init(void)
{
    GPIO_InitTypeDef  GPIO_InitStructure;

    RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB|RCC_APB2Periph_GPIOE, ENABLE);

    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_Init(GPIOB, &GPIO_InitStructure);

    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_Init(GPIOB, &GPIO_InitStructure);

    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_Init(GPIOE, &GPIO_InitStructure);

}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24

函数主体中包含了使能时钟和引脚的GPIO配置等,其模式都比较固定。

上述C代码中配置了三个引脚PB5,PB6和PE5。可以归纳为一张Excel表格led.xlsx如下:
在这里插入图片描述
通过Matlab脚本解析这张表格,提取出GPIO信息,就可以写出对应的led.c文件。

博友如果想运行下面的脚本,可以在Matlab当前路径先新建一个led.xlsx表格,并拷贝下面的表格内容。

GPIOGPIO_PinGPIO_ModeGPIO_Speed
BGPIO_Pin_5GPIO_Mode_Out_PPGPIO_Speed_50MHz
BGPIO_Pin_6GPIO_Mode_Out_PPGPIO_Speed_50MHz
EGPIO_Pin_5GPIO_Mode_Out_PPGPIO_Speed_50MHz

3 示例脚本

这一章节直接把整个生成C文件的函数都贴出来,下一章会一点点的解释博主的思路。

function ManualCode()
%% step1 读取表格信息
[~,~,Excel_Cell] = xlsread('led.xlsx','led');
CodeText = '';

%% step2 将代码内容写入变量CodeText中
%#include头文件
CodeText = [CodeText,'#include  "led.h"',newline,newline];
%函数以及结构体
CodeText = [CodeText,'void LED_Init(void)',newline,'{',newline,'    GPIO_InitTypeDef  GPIO_InitStructure;',newline,newline];
%使能端口时钟
RCCParamater = '';
for row = 2:size(Excel_Cell,1)
    Paramater = ['RCC_APB2Periph_GPIO',Excel_Cell{row,1}];
    if ~contains(RCCParamater,Paramater)
        RCCParamater = [RCCParamater,Paramater,'|'];
    end
end
RCCParamater = RCCParamater(1:end-1);
CodeText = [CodeText,'    RCC_APB2PeriphClockCmd(',RCCParamater,', ENABLE);',newline,newline];
%端口配置
for row = 2:size(Excel_Cell,1)
    CodeText = [CodeText,'    GPIO_InitStructure.GPIO_Pin = ',Excel_Cell{row,2},';',newline];
    CodeText = [CodeText,'    GPIO_InitStructure.GPIO_Mode = ',Excel_Cell{row,3},';',newline];
    CodeText = [CodeText,'    GPIO_InitStructure.GPIO_Speed = ',Excel_Cell{row,4},';',newline];
    CodeText = [CodeText,'    GPIO_Init(GPIO',Excel_Cell{row,1},', &GPIO_InitStructure);',newline,newline];
end
CodeText = [CodeText,'}',newline];

%% step3 将变量CodeText写入led.c文件中
fid = fopen('led.c','w');
fprintf(fid,CodeText);
fclose(fid);
end
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34

4 脚本说明

4.1 step1 读取表格信息

第一步很简单,通过xlsread函数把led.xlsx的表格信息读出来,存放在一个单元数组Excel_Cell中。
在这里插入图片描述
然后建了一个空的字符串变量CodeText,在后面用于不断地写入C文件内容的信息,最后再一股脑地存到文件中。

4.2 step2 将代码内容写入变量CodeText中

这个step是主体部分,会从头到尾一点一点地写C文件的内容。

4.2.1 头文件、函数名、定义结构体

头文件、函数名和定义结构体都是固定的代码,直接写在CodeText变量中就行了。
在这里插入图片描述
脚本运行到这一步,就已经把头文件、函数名、定义结构体写进了CodeText变量中。
在这里插入图片描述

4.2.2 使能端口时钟

使能端口时钟这行代码就和表格的第一列相关了。可以看出一共有B和E两种GPIO引脚。
在这里插入图片描述
所以代码中的参数应该把B和E都带上。
在这里插入图片描述
Matlab脚本中对第一列进行循环和判断,写入CodeText变量。
在这里插入图片描述

4.2.3 端口配置

表格的B,C,D列都是端口配置相关信息,通过一个for循环依次写入。写完以后在变量后面再加个花括号}。
在这里插入图片描述

4.3 step3 将变量CodeText写入led.c文件中

用fopen函数和fprintf函数,把包含文件内容的CodeText字符串写到led.c文件中,就完成了这个代码自动写入的过程。

5 总结

本文的例子比较简单,也几乎没有涉及字符串操作,只是展现了一个基本思路。基本思路就是通过表格管理代码中的一些关键信息,然后通过脚本识别表格的信息,自动写出C文件或头文件。

这个方法的特点是,在前期制作表格模板以及写脚本的过程中需要花费很多时间去调试并改进。等到后期不断迭代之后,脚本工具会非常成熟,只需要维护表格模板,就可以快速地生成某种格式的手写代码。

>>返回个人博客总目录

注:本文转载自blog.csdn.net的chhttty的文章"https://blog.csdn.net/u013288925/article/details/108012680"。版权归原作者所有,此博客不拥有其著作权,亦不承担相应法律责任。如有侵权,请联系我们删除。
复制链接
复制链接
相关推荐
发表评论
登录后才能发表评论和回复 注册

/ 登录

评论记录:

未查询到任何数据!
回复评论:

分类栏目

后端 (14832) 前端 (14280) 移动开发 (3760) 编程语言 (3851) Java (3904) Python (3298) 人工智能 (10119) AIGC (2810) 大数据 (3499) 数据库 (3945) 数据结构与算法 (3757) 音视频 (2669) 云原生 (3145) 云平台 (2965) 前沿技术 (2993) 开源 (2160) 小程序 (2860) 运维 (2533) 服务器 (2698) 操作系统 (2325) 硬件开发 (2492) 嵌入式 (2955) 微软技术 (2769) 软件工程 (2056) 测试 (2865) 网络空间安全 (2948) 网络与通信 (2797) 用户体验设计 (2592) 学习和成长 (2593) 搜索 (2744) 开发工具 (7108) 游戏 (2829) HarmonyOS (2935) 区块链 (2782) 数学 (3112) 3C硬件 (2759) 资讯 (2909) Android (4709) iOS (1850) 代码人生 (3043) 阅读 (2841)

热门文章

101
推荐
关于我们 隐私政策 免责声明 联系我们
Copyright © 2020-2024 蚁人论坛 (iYenn.com) All Rights Reserved.
Scroll to Top