您现在的位置是:首页 > 唯美句子

C++从入门到精通——内联函数

作者:璐璐时间:2024-04-08 09:15:39分类:唯美句子

简介  文章浏览阅读888次,点赞50次,收藏46次。内联函数是一种优化手段,通过在编译时将函数调用替换为函数体本身的复制品,以减少函数调用的开销。它适用于函数体较小、调用频繁的情况。使用内联函数可以提高程序执行效率,但也会增加最终生成的代码大小。在C++中,可以使用

点击全文阅读

内联函数

前言一、内联函数概念为什么会出现内联函数C语言使用宏定义编写两数交换 内联函数的概念 二、内联函数的查看方式三、内联函数的特性四、关于内联函数的题目宏的优缺点C++有哪些技术替代宏


前言

内联函数是一种优化手段,通过在编译时将函数调用替换为函数体本身的复制品,以减少函数调用的开销。它适用于函数体较小、调用频繁的情况。使用内联函数可以提高程序执行效率,但也会增加最终生成的代码大小。在C++中,可以使用inline关键字声明内联函数。然而,编译器对于是否真正内联一个函数有最终决定权,即使函数被声明为内联,编译器也可以选择不进行内联。


一、内联函数概念

为什么会出现内联函数

C语言使用宏定义编写两数交换

引例:C语言可以使用宏定义实现两数交换的功能。下面是一个示例的代码:

#include <stdio.h>#define SWAP(a, b)  do { \                        int temp = a; \                        a = b; \                        b = temp; \                    } while (0)int main() {    int num1 = 10;    int num2 = 20;    printf("Before swap: num1 = %d, num2 = %d\n", num1, num2);    SWAP(num1, num2);    printf("After swap: num1 = %d, num2 = %d\n", num1, num2);    return 0;}

这段代码中定义了一个宏 SWAP,使用 do-while 循环实现交换。在 main 函数中声明了两个变量 num1num2,然后调用 SWAP 宏进行交换,最后打印结果。运行程序,输出如下:

Before swap: num1 = 10, num2 = 20After swap: num1 = 20, num2 = 10

C++中引入了内联函数的概念,主要是为了提高程序的性能。在C语言中没有内联函数的概念,我们通常会使用宏定义来实现,但是宏定义的写法过于困难,如上所示的宏定义实现的交换,所以便在C++中便提出内联函数这个概念,来替代宏定义写的函数。

内联函数的作用是在编译时将函数的代码嵌入调用的地方,而不是通过函数调用的方式执行。

内联函数的优点有以下几点:

减少函数调用的开销:函数调用会涉及到栈的操作、参数传递和返回值的处理等,而内联函数的代码直接嵌入到调用的地方,避免了这些开销。

减少函数调用带来的代码膨胀:函数调用会导致代码中出现大量的跳转指令,而内联函数的代码直接嵌入到调用的地方,可以减少跳转指令的数量,使代码更加紧凑。

提高缓存命中率:内联函数的代码嵌入到调用的地方,可以减少函数调用时的跳转,使得程序的指令更加连续,更有可能被CPU缓存命中,提高程序的执行效率。

需要注意的是,内联函数适用于函数体较小、频繁调用的情况。对于函数体过大或者调用频率较低的函数,使用内联可能会导致代码膨胀、降低缓存命中率,反而影响性能。因此,使用内联函数需要根据具体情况进行权衡和选择。

内联函数的概念

inline修饰的函数叫做内联函数,编译时C++编译器会在调用内联函数的地方展开,没有函数调用建立栈帧的开销,内联函数提升程序运行的效率。
在这里插入图片描述
如果在上述函数前增加inline关键字将其改成内联函数,在编译期间编译器会用函数体替换函数的调用。

二、内联函数的查看方式

release模式下,查看编译器生成的汇编代码中是否存在call Adddebug模式下,需要对编译器进行设置,否则不会展开(因为debug模式下,编译器默认不会对代码进行优化,以下给出vs2013的设置方式)

在这里插入图片描述

在这里插入图片描述

三、内联函数的特性

inline是一种以空间换时间的做法,如果编译器将函数当成内联函数处理,在编译阶段,会用函数体替换函数调用 缺陷:可能会使目标文件变大优势:少了调用开销,提高程序运行效率 inline对于编译器而言只是一个建议,不同编译器关于inline实现机制可能不同 一般建议:将函数规模较小(即函数不是很长,具体没有准确的说法,取决于编译器内部实现)、不是递归、且频繁调用的函数采用inline修饰,否则编译器会忽略inline特性。下图为《C++prime》第五版关于inline的建议:
在这里插入图片描述 inline不建议声明和定义分离,分离会导致链接错误。因为inline被展开,就没有函数地址了,链接就会找不到。
// F.h#include <iostream>using namespace std;inline void f(int i);// F.cpp#include "F.h"void f(int i){ cout << i << endl;}// main.cpp#include "F.h"int main(){ f(10); return 0;}// 链接错误:main.obj : error LNK2019: 无法解析的外部符号 "void __cdecl f(int)" (?f@@YAXH@Z),该符号在函数 _main 中被引用

对于这种情况,我们可以直接在头文件中直接定义

inline void f(int i){ cout << i << endl;}

四、关于内联函数的题目

宏的优缺点

优点:
1.增强代码的复用性。
2.提高性能。缺点:
1.不方便调试宏。(因为预编译阶段进行了替换)
2.导致代码可读性差,可维护性差,容易误用。
3.没有类型安全的检查 。

C++有哪些技术替代宏

常量定义 换用const 或 enum短小函数定义 换用内联函数

点击全文阅读

郑重声明:

本站所有活动均为互联网所得,如有侵权请联系本站删除处理

我来说两句