1. 内联函数
调用函数一般比对等价表达式求值要慢。因为调用函数除了对表达式求值外,还包含一系列过程,包括堆栈建立、拷贝实参、跳转执行等等。而在程序之中,通常存在一些优化规模较小、流程直接、却调用频率很高的函数,我们可以通过在函数声明前添加inline
关键字将这些函数来定义为内联函数。内联函数将于编译时,在调用处完整展开,进而消除函数调用开销。
inline string& shortestString(string &s1, string &s2){
return s1.size() < s2.size()? s1 : s2;
}
string a = "abc";
string b = "abcd";
string c = shortestString(a, b) + "efg";
// 编译时内联展开,等价于 string c = (s1.size() < s2.size()? s1: s2) + "efg";
需要注意的是,inline
关键字通常只是向编译器提出一个建议,函数并不一定会被内联展开。(比如,需要内联的函数逻辑复杂且行数众多)
2. constexpr函数
constexpr
是指能够用于常量表达式初始化的函数。除了在函数声明中使用constexpr
关键字之外,constexpr函数条件达成还必须遵守一些规则。这些规则随着C++标准处于变化状态,而C++ Primer上的一些内容在最新标准下以不再适用(除非指定编译器支持版本为C++ 11)。因此我在这里截取了一些cpprefrence上的内容以作补充。
当使用constexpr
函数初始化常量表达式时,其结果通常会被编译器在调用处展开,因此constexpr
函数会被隐式指定为内联函数。
因为内联函数和constexpr函数是要在编译器进行展开的,因此允许在程序中多个头文件中反复声明、定义,但是其多次定义的内容必须保持一致。