__BEGIN_DECLS 和__END_DECLS

19 篇文章 2 订阅

在底层代码和库的头文件中经常看到 __BEGIN_DECLS 和 __END_DECLS这两个宏,一直不太理解,今天特意查了一下,才知道它有这么大的用处。 
首先看一下他们的宏定义:

sys/cdefs.h

#if defined(__cplusplus)
    #define __BEGIN_DECLS   extern "C" {
    #define __END_DECLS     }
#else
    #define __BEGIN_DECLS
    #define __END_DECLS

我们编写代码,经常需要c和c++混合使用,为了使 C 代码和 C++ 代码保持互相兼容的过程调用接口,需要在 C++ 代码里加上 extern “C” 作为符号声明的一部分,为了简化,从而定义了上面的两个宏方便我们使用。

1. extern "C"

extern "C"的主要作用就是为了能够正确实现C++代码调用其他C语言代码。

加上extern "C"后,会指示编译器这部分代码按C语言的进行编译,而不是C++的。由于C++支持函数重载,因此编译器编译函数的过程中会将函数的参数类型也加到编译后的代码中,而不仅仅是函数名;而C语言并不支持函数重载,因此编译C语言代码的函数时不会带上函数的参数类型,一般只包括函数名。

可以把其看成extern 和 “C”:

1.1 extern

代表是声明为外部,即定义的地方可能不在当前作用域。

例如,在函数内部声明:

int func()
{
    extern int a;
    ...
    ...
}

变量 a 定义在别的地方,可能是func 下面,也可能在func所在文件外面。

extern 修饰的函数也是一样,不过函数定义的地方就是有函数体的地方。一般extern修饰的函数在头文件中,函数体放在c文件中,这样就实现了声明和定义分离。

1.2 “C”

这里表示声明的部分是C部分。C++是C的超集,当时C和C++编译器不同,因为C++中存在函数的重载,所以在编译的时候会变成函数名加上参数类型,而C编译的时候只是函数名。

例如:

void func(int, int);

在C++编译后,目标文件中函数符号名变成__func_int_int,而C编译后仅为__func。

所以,如果C++中使用C中的函数,不做声明的时候是提示找不到该函数,因此,C++中想要使用C接口(在C的编译工具链编译出来的目标文件中),需要加上声明,如下:

#ifdef __cplusplus
extern "C" {
#endif
 
void fun(int, int);
 
#ifdef __cplusplus
}
#endif

  • 5
    点赞
  • 12
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

私房菜

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值