使用函数组织代码

使用函数处理不同类型的数据

函数重载

​ 名称和返回类型相同,但参数不同的函数被称为重载函数。

将数组传递给函数

​ 显示一个整数的函数类似于下面这样: void DisplayInteger(int Number); 显示整型数组的函数的原型稍微不同: void DisplayIntegers(int[] numbers, int Length); 第一个参数告诉函数,输入的数据是一个数组,而第二个参数指出了数组的长度,以免您使用数组时跨越边界。

按引用传递参数

code1

24: // Function definitions (implementations) 
25: double Area(double radius) 
26: { 
27: return Pi * radius * radius; 
28: } 

code2

// output parameter result by reference 
void Area(double radius, double& result) 
{ 
 result = Pi * radius * radius; 
}

​ 注意到该 Area( )函数接受两个参数。别遗漏了第二个形参 result 旁边的&,它告诉编译器,不要将 第二个实参复制给函数,而将指向该实参的引用传递给函数。返回类型变成了 void,因为该函数不再 通过返回值提供计算得到的面积,而按引用以输出参数的方式提供它。

微处理器如何处理函数调用

​ 在微处理器级,函数调用是如何实现的呢?虽然确切地了解这一点不是非常重要,但您可能发现 它很有趣。了解这一点有助于明白 C++为何支持本节后面将介绍的内联函数

理解栈

栈是一种后进先出的内存结构,很像堆叠在一起的盘子,您从顶部取盘子,这个盘子是最后堆叠上 去的。将数据加入栈被称为压入操作;从栈中取出数据被称为弹出操作。栈增大时,栈指针将不断递增, 始终指向栈顶,如图 7.3 所示。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-SzXtGcSj-1721718554832)(https://i-blog.csdnimg.cn/direct/df364afc089744e4a636430d7a18a2b5.png#pic_center)]

图 7.3 包含三个整数的栈的可视化表示

栈的性质使其非常适合用于处理函数调用。函数被调用时,所有局部变量都在栈中实例化,即被压 入栈中。函数执行完毕时,这些局部变量都从栈中弹出,栈指针返回到原来的地方。

内联函数

double GetPi() 
{ 
 return 3.14159; 
} 

​ 相对于实际执行 GetPi( )所需的时间,执行函数调用的开销可能非常高。这就是 C++编译器允许程序员将这样的函数声明为内联的原因。程序员使用关键字 inline 发出请求,要求在函数被调用时就地
展开它们:

inline double GetPi() 
{ 
 return 3.14159; 
}

​ 请求将函数 DoubleNum()的内容直 接放到调用它的地方(第 16 行),以提高代码的执行速度。 将函数声明为内联的会导致代码急剧膨胀,在声明为内联的函数做了大量复杂处理时尤其如此。应 尽可能少用关键字 inline,仅当函数非常简单,需要降低其开销时(如前面所示),才应使用该关键字。

​ 大多数较新的 C++编译器都提供了各种性能优化选项。有些提供了优化大小或速度的选 项,如 Microsoft C++编译器。为内存弥足金贵的设备和外设开发软件时,优化代码的大 小至关重要。优化代码大小时,编译器可能拒绝众多的内联请求,因为这会让代码急剧 膨胀。

自动推断返回类型

​ 从 C++14 起,这种做法也适用于函数:使用 auto 让编译器根据您返回的值来推断函数的返回类型,而不直接指 定返回类型。

​ 对于依赖于返回类型自动推断的函数,必须先定义(即实现)再调用。这是因为调用函 数时,编译器必须知道其返回类型。如果这种函数包含多条 return 语句,必须确保根据 它们推断出的返回类型都相同。另外,在递归调用后面,至少得有一条 return 语句。

lambda 函数

​ lambda 函数是 C++11 引入的,有助于使用 STL 算法对数据进行排序或处理。排序函数要求您提供 一个二元谓词,以帮助确定元素的顺序。二元谓词是一个这样的函数,即对两个参数进行比较,并在 一个小于另一个时返回 true,否则返回 false。

问与答

问:如果递归函数不终止,结果将如何?
答:程序将不断执行下去。程序不断执行下去也许不是坏事,因为 while(true)和 for(;;)循环也会导致这种后果。然而,递归函数调用将占用越来越多的栈空间,而栈空间有限,终将耗尽。最终,应用程序将因栈溢出而崩溃。

问:既然将函数声明为内联的可提高执行速度,为何不将所有函数都声明为内联的?
答:这样看情况而定。然而,如果将在多个地方使用的函数声明为内联的,将在调用它的每个地方放置其内容,这将导致代码急剧膨胀。另外,根据性能设置,大多数较新的编译器都能判断应内联哪些函数,进而为程序员这样做。

问:可给函数的所有参数都提供默认值吗?
答:绝对可以,在合理的情况下也推荐这样做。

问:我有两个函数,它们都叫 Area,其中一个接受半径作为参数,另一个接受高度作为参数,但我希望一个返回 float 值,另一个返回 double 值。这可行吗?
也推荐这样做。

问:我有两个函数,它们都叫 Area,其中一个接受半径作为参数,另一个接受高度作为参数,但我希望一个返回 float 值,另一个返回 double 值。这可行吗?
答:重载函数时,函数必须同名,且返回类型相同。就这里的情形而言,编译器将报错,因为它要求这两个函数的名称不同。

  • 25
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值