从零开始学Visual C++
上QQ阅读APP看本书,新人免费读10天
设备和账号都新为新人

1.5 函数

在面向对象编程(OOP)出现之前,函数(function)是程序的基本组成单元,如Windows API(Application Program Interface,应用程序编程接口)就是一组数量庞大的函数库,MFC(Microsoft Foundation Class,微软基本类库)类库将功能相关的API函数封装到一个类中,可以通过类成员函数方式调用,也可直接调用全局API函数,效果是一样的。

1.5.1 什么是函数

函数可看做是一组代码的集合,调用一个函数后,自动执行该函数内的代码。函数可以有多个输入参数和一个返回值,类似于数学公式y=ax1+bx2+cx3+d,其中x1、x2、x3是输入参数, y是返回值,在函数体内编写具体的算法步骤。

调用函数时,传递输入参数,执行完毕后函数返回一个值,若返回值类型为void,则无返回值。使用C++自带的函数库和已写好的函数模块可以大大提高开发效率,不用为某个功能的具体实现影响开发进度,在实际开发中,尽可能使用成熟稳定的函数代码。

1.5.2 定义函数

函数由函数名、参数列表、返回值、函数体组成,函数名应使用有意义的命名,根据名称即可大致了解其用途。参数值可有0个或多个,由参数类型和参数名组成,不同参数用逗号分隔。返回值决定函数返回类型,若为void,表示无返回值,否则,需要用return语句返回一个同类型的值。

函数原型:返回值函数名(类型 参数1,类型 参数2,……){函数体 }

例如:int GetMax(int a,int b){ if(a>b) return a; else return b; }

1.5.3 变量作用域

函数体内不同位置的变量具有不同的作用域,在函数体外的变量为全局变量(Global),全局变量在函数内任何位置都有效。作用域可根据{}语句块判定,在块之前定义的变量在块内可用,在块之后定义的变量在块内不可用。

【实例1-18】全局变量、局部变量的作用域。

        #include <iostream>
        using namespace std;
        int global=10;                    //全局变量
        int main()
        {
            int outBlock=12;              //块外变量
            if(outBlock>1)
            {
                int inBlock=20;           //块内变量
            }
            return 0;
        }

global作为全局变量,在main函数内部任何位置都可用。outBlock在main块内、if块外,因此outBlock在main块外不可用,在main块内定义位置后所有地方都可用。inBlock在if块内定义,仅在if块内可用。

1.5.4 使用函数

自定义的函数必须在定义位置之后才能使用,若在定义位置之前使用,需要做函数声明(declare),函数声明只需表明函数名、返回值、参数类型,不需要参数名称。

函数若有参数,使用时需传递相同类型的参数值,用赋值运算符接收函数返回值。调用函数时,程序流程进入函数内部,执行完函数体后返回调用位置处。

【实例1-19】创建自定义函数sum,在主函数main中调用该函数,并输出返回值。

        #include <iostream>
        using namespace std;
        int sum(int,int=10);              //在定义位置之前调用,要做函数声明,第2个参数默认为10
        int main()
        {
            cout<<sum(100,20)<<endl;      //调用自定义函数
            cout<<sum(100)<<endl;         //使用默认参数值
            return 0;
        }
        int sum(int a,int b)              //函数定义
        {
            return a+b;                   //返回值
        }

自定义的sum函数的参数a和b是形式参数,在调用时将实际参数的值复制传入函数,由于传递实际参数的复制,在函数内部对参数值的任何改变都不会影响实际参数的值。

若想改变实际参数的值,可将函数的参数改为指针类型或引用类型,传入实际参数的内存地址,通过内存地址,函数内部的修改直接针对指定内存地址上的变量,这样函数内部的修改就可以影响实际参数的值。

函数的参数可以有默认值,在函数声明时指定默认值,如int sum(int,int=10);有默认值的参数必须在参数列表尾处。调用函数时有默认值的参数可不传入,如sum(100),第1个参数为100,第2个参数为默认的20,若传入两个参数值,则用传入第2个参数值替代默认值。默认参数在函数的参数较多时很有作用,免去每次都输入冗长的无关紧要的参数。

1.5.5 函数重载

函数重载(overload)可以使多个函数名称相同,但参数列表不同,例如函数sum计算两个数值的和,数值类型可能为整数、浮点数以及其他可以求和的类型,若分别使用不同的函数名,造成命名复杂且难以记忆,使用函数重载后只需记住一个函数名,调用时传入指定类型的参数即可。

【实例1-20】重载sum函数,可用于整型、浮点型两种类型的求和计算。

        #include <iostream>
        using namespace std;
        int sum(int a,int b){                         //整型计算
            return a+b;
        }
        double sum(double a,double b){                //浮点型计算
            return a+b;
        }
        int main()
        {
            cout<<sum(100,20)<<endl;                  //调用整型版本
            cout<<sum(123.5,32.6)<<endl;              //调用浮点版本
            return 0;
        }

定义了两个版本的sum函数,分别用于整型、浮点型的求和计算。程序执行时根据参数类型自动选择匹配版本的函数,如sum(100,20)调用整型版本,sum(123.5,32.6)调用浮点版本。