OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 2812|回复: 1

希望高手帮忙讲解以下两种情况的利弊

[复制链接]

26

主题

201

帖子

0

精华

高级会员

Rank: 4

积分
606
金钱
606
注册时间
2013-12-14
在线时间
125 小时
发表于 2015-12-7 16:33:40 | 显示全部楼层 |阅读模式
5金钱
第一种:使用宏定义
#define  BspGPIO_Led_On()            GPIO_SetBits(GPIOA, GPIO_Pin_0)

第二种:函数
void  BspGPIO_Led_On(void)
{
     GPIO_SetBits(GPIOA, GPIO_Pin_0);
}

最佳答案

查看完整内容[请看2#楼]

宏定义就是在代码中直接进行替换,如果你的main中有10个BspGPIO_Led_On(),就等同于有10个GPIO_SetBits(GPIOA, GPIO_Pin_0)语句,直接执行,不需要进行函数调用,不需要进行压栈操作。 函数调用需要进行压栈操作,运行结束之后还需要出栈,返回原来的函数继续运行,但GPIO_SetBits(GPIOA, GPIO_Pin_0)这个语句只有一个。 在楼主这个例子中,使用宏定义会好一点:只有一个语句,如果是经常被调用,可以减少压栈出栈的时 ...
正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

9

主题

538

帖子

0

精华

论坛元老

Rank: 8Rank: 8

积分
3371
金钱
3371
注册时间
2015-1-7
在线时间
794 小时
发表于 2015-12-7 16:33:41 | 显示全部楼层
宏定义就是在代码中直接进行替换,如果你的main中有10个BspGPIO_Led_On(),就等同于有10个GPIO_SetBits(GPIOA, GPIO_Pin_0)语句,直接执行,不需要进行函数调用,不需要进行压栈操作。

函数调用需要进行压栈操作,运行结束之后还需要出栈,返回原来的函数继续运行,但GPIO_SetBits(GPIOA, GPIO_Pin_0)这个语句只有一个。

在楼主这个例子中,使用宏定义会好一点:只有一个语句,如果是经常被调用,可以减少压栈出栈的时间,运行效率快。
如果宏定义的内容很多(函数内容很多),用函数可以节约代码开销,只有一个实体,如果用宏的话将会把所用的代码复制多次。

对于函数的形式,可以使用inline修饰函数,这样可以起到宏一样的效果(无压栈出栈,直接替代)


用宏定义有另外一个问题,就是如果将宏编译成库,那这个宏的实体也会被编译进去,导致无法修改,举例说
你把#define  BspGPIO_Led_On()            GPIO_SetBits(GPIOA, GPIO_Pin_0)编译到库中,
然后你在工程中再定义#define  BspGPIO_Led_On()            GPIO_SetBits(GPIOA, GPIO_Pin_1),修改管脚0到管脚1,这个时候是不行的,因为管脚0已经被编译进去了。
而如果使用函数void  BspGPIO_Led_On(void)
{
     GPIO_SetBits(GPIOA, GPIO_Pin_0);
}
被编译进库,那你再工程中重新编写函数
void  BspGPIO_Led_On(void)
{
     GPIO_SetBits(GPIOA, GPIO_Pin_1); 
}
就能将管脚0重新定位到管脚1.
机器生汇编,汇编生B,B生C,C生万物.... 经过长期对C语言的研究,目前只有两个方面不懂:这也不懂,那也不懂
https://github.com/ianhom
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /2 下一条

正点原子公众号

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2025-6-21 04:13

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表