C++内联函数通常是跟类一起使用。如果一个函数是内联的,那么在编译时,编译器会把该函数的代码副本放在每个调用该函数的地方。对内联函数进行任何修改,都需要重新编译函数的所有客户端,因为编译器需要重新更改一次所有的代码,否则将会继续使用旧的代码。
如果想把一个函数定义为内联函数,需要在函数名前面放关键字inline,在调用函数之前需要对函数进行定义。如果已定义的函数多于一行,编译器会忽略inline限定符。
在类定义中的函数都是内联函数,即使没有使用inline说明符。
inline函数的使用:
/*** inline.cpp ***/ #include<iostream> using namespace std; inline int Max(int x,int y) { return (x > y) ? x : y; } int main() { cout << "Max (20,10): " << Max(20,10) << endl; cout << "Max (0,200): " << Max(0,200) << endl; cout << "Max(100,1010): " << Max(100,1010) << endl; return 0; }
运行结果:
exbot@ubuntu:~/wangqinghe/C++/20190807$ ./inline
Max (20,10): 20
Max (0,200): 200
Max(100,1010): 1010
引入内联函数的目的就是为解决程序中函数调用的效率问题。
程序在编译器编译的时候,编译器将程序中出现的内联函数的调用表达式用内联函数的函数体进行替换。而对于其他函数,都是在运行的时候才被替代。其实就是用空间代价来换取节省时间的效果。所以内联函数一般都是1-5行的小函数。
在使用内联函数时要留神:
- 在内联函数中不允许使用循环语句和开关语句;
- 内联函数的定义必须出现在内联函数的第一次调用之前;
- 类结构中所在的类说明内部定义的函数是内联函数。
Tips:只有当函数在只有10行甚至更少时才会被定义为内联函数。
定义:当函数被声明为内联函数之后,编译器会将其内联展开,而不是按照通常的函数调用机制进行调用。
优点:当函数体比较小时,内联该函数可以令目标代码更加高效。对于存取函数以及其他函数体比较短,性能关键的函数,鼓励使用内联。
缺点:滥用内联函数将导致程序变慢,内联可能使目标代码量或增或减,这取决于内联函数的大小。内联函数非常短小的存取函数通常会减少代码大小,但内联一个相当大的函数将戏剧性的增加代码大小。现代处理器由于更好的指令缓存,小巧的代码往往执行更快。
结论:一个较为合理的经验准则是,不要超过10行的函数。谨慎对待析构函数,析构函数往往比其表面看起来更长,因为有隐含的成员和基类析构函数被调用。
内联那些包含循环或switch语句的函数往往得不偿失。
有些函数即使声明为内联也不一定会被编译器内联,这点很重要。比如虚函数和递归函数就不会被正常内联。通常,递归函数不应该声明成内联函数(递归调用堆栈的展开并不像循环那么简单,比如递归层数在编译时可能是未知的,大多说编译器都不支持内联递归函数)。虚函数内联的主要原因则是想把它的函数体放在类定义内,为了图个方便,抑或是当作文档描述其行为,比如精短的存取函数。