打印
[牛人杂谈]

C/C++内联函数和extern "C"问题讨论

[复制链接]
666|8
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
zhuomuniao110|  楼主 | 2016-10-26 20:42 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
内联(inline)函数
       提到内联函数,先看下面两个程序,程序的执行结界都是为了得到两个值相加之和:
int add(int x,int y)
{
    return x+y;
}

int main(int argc,char* argv[])
{
    int a=1,b=2,c;
    c=add(a,b);          //通过调用函数的形式得到相加结果
    return 0;
}

//程序2
int main(int argc,int argv[])
{
    int a=1,b=2,c;
    c=a+b;               //直接计算得到相加结果  
    return 0;
}


沙发
zhuomuniao110|  楼主 | 2016-10-26 20:43 | 只看该作者
上面哪个程序的执行效率更高?
      答案是“程序2”是c=a+b直接计算得到相加结果,而“程序1”是通过函数调用c=add(a,b)得到相加的结果。“程序2”的直接计算,节省了函数调用、参数传值、控制权转移等开销,执行效率比“程序1”的函数调用要快得多。
      然而,实际工作中,可能会更多地采用“程序1”的函数调用方式,因为从功能封装和重复使用上来说,通常会将一段通用的程序片段进行封装,以便在其他需要相同功能的地方调用。这就产生了一个矛盾,如果将一段特定功能的代码封装成一个函数,就会大大降低程序效率。
      为了解决这个问题,C++引入了内联函数的概念。内联函数给出了一种解决方案:如果一个函数被指定为内联(inline)函数,则它将在调用点上被“内联”地展开,内联函数不是在调用时发生控制转移,而是在编译时将函数体嵌入在调用处。
       这意味着,编写代码时,可以采用“程序1”的函数调用形式,等到编译时,编译器会把“程序1”方式编译成“程序2”的方式,这就是内联函数的优点所在。唯一要做的就是,在“程序1”中加入关键字inline。

//程序3
inline int add(int x,int y)  //声明为内联(inline)函数
{
    return x+y;
}

int main(int argc,char* argv[])
{
    int a=1,b=2,c;
    c=add(a,b);         
    return 0;
}
注意:所谓inline函数,只是对C++编译器的一个建议。C++编译器可以选择忽略这个建议,比如对于大于1200行的函数,或者递归调用的函数,或者用到递归调用的函数,通常C++编译器都不会编译成内联函数。

extern "C"
      时常在C++的代码之中看到这样的代码:
#ifdef _cplusplus 
extern "C" {
#endif

//一段代码

#ifdef _cplusplus
}
#endif




使用特权

评论回复
板凳
zhuomuniao110|  楼主 | 2016-10-26 20:44 | 只看该作者
这样的代码到底是什么意思呢?首先,_cplusplus是C++中的自定义宏,那么定义了这个宏则表示这是一段C++的代码,也就是说,上面的代码的含义是:如果这是一段C++的代码,那么加入extern "C"{和}处理其中的代码。
      要明白为何使用extern "C",还得从C++中的重载函数入手。在C++中,为了支持重载机制,在编译生成的汇编码中,要对函数的名字进行一些处理,加入比如函数的返回类型等等。而在C中,只是简单的函数名字而已,不会加入其他的信息。也就是说:C++和C对产生的函数名字的处理是不一样的。所以,一句话,加入extern "C"是防止名字改编。
      C和C++对函数的处理方式是不同的。extern "C"是使C++能够调用C写的库文件的一个手段,如果要对编译器提示使用C的方式来处理函数的话,那么就要使用extern "C"来说明。

使用特权

评论回复
地板
Roderman_z| | 2016-10-26 21:22 | 只看该作者
默认都是内联的函数吧

使用特权

评论回复
5
mintspring| | 2016-10-27 11:44 | 只看该作者
第一次了解这个概念,很深奥。

使用特权

评论回复
6
mintspring| | 2016-10-27 11:45 | 只看该作者
内联函数从源代码层看,有函数的结构,而在编译后,却不具备函数的性质。内联函数不是在调用时发生控制转移,而是在编译时将函数体嵌入在每一个调用处。编译时,类似宏替换,使用函数体替换调用处的函数名。一般在代码中用inline修饰,但是能否形成内联函数,需要看编译器对该函数定义的具体处理。

使用特权

评论回复
7
diweo| | 2016-10-27 20:56 | 只看该作者
Roderman_z 发表于 2016-10-26 21:22
默认都是内联的函数吧

在类定义内部定义的函数是默认内联的,其他函数默认不内联。

使用特权

评论回复
8
zhuomuniao110|  楼主 | 2016-10-30 15:37 | 只看该作者
以前不懂具体什么意思,总是看到in line,这个概念,专门找了资料学习,并分享给大家。

使用特权

评论回复
9
zhuomuniao110|  楼主 | 2016-11-13 22:00 | 只看该作者
C 语言这么牛叉,你不深入研究是无法理解的。

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

188

主题

3247

帖子

10

粉丝