Loading... # 函数基础 一个典型的函数(function)定义包括以下部分:返回类型(return type)、函数名字、由0个或多个形参(parameter)组成的列表以及函数体。其中形参以逗号隔开,形参的列表位于一对圆括号之内。函数执行的操作在语句块中说明,该语句块称为函数体(function body)。 <br> 我们通过**调用运算符(call operator)**来执行函数。调用运算符的形式是一对圆括号,它作用于一个表达式,该表达式是函数或者指向函数的指针;圆括号之内是一个用逗号隔开的实参(argument)列表,我们用实参初始化函数的形参。调用表达式的类型就是函数的返回类型。 ## 编写函数 ```cpp int test(int a){ //(int a)形参 a++; //进行自增 return a; //返回结果 } ``` 函数的名字是test,它作用于一个整型参数,返回一个整型值。在函数中将<kbd>a</kbd>的值加1.return 语句负责结束test并返回<kbd>a</kbd>的值。 <br> ## 调用函数 要调用test函数,**必须**提供一个整数值,调用得到的结果也是一个整数: ```cpp #include<iostream> using namespace std; int main(){ int b = test(4); //这里调用了函数test,4是实参 cout << b << endl; //b=5,在调用函数时,4进行了自增 return 0; } ``` 函数的调用完成主要两项工作:一是用实参初始化函数对应的实参,二是将控制权转移给被调用的函数。此时,**主调函数(calling function)**的执行被中断,被调函数(called function)开始执行。 <br> 执行函数的第一步是(隐式地)定义并初始化它的形参。因此,当调用test函数时,首先创建一个名为<kbd>a</kbd>的int类型变量,然后将它初始化为调用时所用的实参4。 <br> 当遇到一条return语句时函数结束执行过程。和函数调用一样,return语句也完成两项工作:一是返回<kbd>return</kbd>语句中的值(如果有的话),二是将控制权从调用函数转移回主调函数。函数的返回 值用于初始化调用表达式的结果,之后继续完成调用所在表达式的剩余部分。 不使用函数时: ```cpp #inclde<iostream> using namespace std; int main(){ int b = 4; b++; cout << b << endl; return; } ``` # 形参和实参 实参是形参的初始值。第一个实参初始化第一个形参,第二个实参初始化第二个形参,以此类推。尽管实参形参存在对应关系,但是并没有规定实参的求值顺序。编译器能以如何可行的顺序对应实参求值。 <br> **实参的类型必须与对应的形参类型匹配**,这一点与之前的规则是一致的,我们知道在初始化的过程中初始值的类型也必须与初始化对象的类型匹配。**函数有几个形参,我们就必须提供相同数量的实参**。因为函数的调用规定实参数量与形参数量一致,所以形参**一定会被初始化**。 <br> 在上面的例子中,test函数只有一个int类型的形参,所以我们每次调用它的时候,我们都必须提供一个能转化成<kbd>int</kbd>的实参 ```cpp tset("hello word"); //错误:实参类型不正确 test(); //错误:实参数量不足 test(42,10,0); //错误:实参数量过多 test(3.14); //正确:该实参能转化成int类型 ``` 因为不能将**const char\***转换成<kbd>int</kbd>,所以第一个调用失败。第二个和第三个调用也会失败,不过错误原因与第一个不同,它们是因为传入的实参数量不对。要想调用test函数只能使用一个实参,只要实参数量不是一个,调用都将失败。最后一个调用是合法的,因为<kbd>double</kbd>可以转换成<kbd>int</kbd>。执行调用时,实参隐式地转换成<kbd>int</kbd>类型(截去小数部分),调用的等价于`test(3);` ## 函数的形参列表 函数的形参列表可以为空,但是不能省略。要想定义一个不带形参的函数,最常用的办法就是书写一个空的形参列表。不过为了与C语言兼容,也可以用关键字**void**表示函数没有形参: ```cpp void f1 () { /* . . . */ } // 隐式地定义空形参列表 void f2 (void) { /* . . . */ } // 显示地定义空形参列表 ``` 形参列表中的形参通常用逗号隔开,其中每个形参都是含有一个声明符的声明。即使两个形参的类型一样,也**必须**把两个类型都写出来: ```cpp int f3 (int v1, v2) { /* . . . */ } //错误 int f4 (int v1, int v2) { /* . . . */} //正确 ``` 任意两个形参都不能同名,而且函数最外层作用域中的局部变量也不能使用与函数形参一样的名字。 形参名是可选的,但是由于我么们无法使用未命名的形参,所以形参一般都应该有个名字。偶尔,函数确实有个别形参不会被用到,则此类形参通常不命名以表示在函数体内不会使用它。不管怎样,是否设置未命名的形参并不影响调用时提供的实参数量。即使某个形参不被函数使用,也必须为它提供一个实参。 # 函数返回类型 大多数类型都能用作函数的返回类型。一种特殊的返回类型是**void**,它表示函数不返回任何值。函数的返回类型**不能是数组类型或则函数类型**,但可以是指向数组或函数的指针。 # 总结 - **函数的定义**:返回类型(return type)、函数名字、由0个或多个形参(parameter)组成的列表以及函数体。 - **调用运算符**:调用运算符的形式是一对圆括号<kbd>()</kbd>,作用于一个表达式,该表达式是函数或者指向函数的指针。 - 圆括号内是用逗号隔开的**实参**(argument)列表。 - 函数调用过程: - 1.主调函数(calling function)的执行被中断。 - 2.被调函数(called function)开始执行。 - **形参和实参**:形参和实参的个数和类型必须匹配上。 - **返回类型**: <kbd>void</kbd>表示函数不返回任何值。函数的返回类型不能是数组类型或者函数类型,但可以是指向数组或者函数的指针。 - **名字**:名字的作用于是程序文本的一部分,名字在其中可见。 最后修改:2024 年 03 月 17 日 © 允许规范转载 打赏 赞赏作者 支付宝 赞 如果觉得我的文章对你有用,请随意赞赏