关于C++中的函数重载问题
1.前言
重载其实在是一个很基础的概念,我们用的时候也很多,但是我老是忘记相关的约定约束,下面就自己学习的相关问题做一个整理吧,主要说明函数重载的含义、函数重载的形式等问题。
参考书籍:《C++ primer》
2.直蹦主题
2.1 什么是重载?
简而言之,如果同一作用域的几个函数名字相同,但形参列表(参数类型和数量)不同,则称为重载函数。需要注意的是,我们定义重载函数的目的往往是因为一些函数的功能类似,而形参不同,如下:
void print(int a);
void print(double a);
2.2 重载规则
1)main函数不能重载;
2)参数列表不同是指参数类型和数量的不同,但不包括返回值;
void fun(int a); // 正确,形参类型为int
void fun(double a); // 正确,形参类型为double
void fun(double a, double b); // 正确, 两个参数
bool fun(double a, double b); // 错误,与上一个比只是返回类型不同
3)顶层的const形参无法和另一个没有顶层const的形参区分开来(我觉得这个有点难理解hhh);
顶层const与底层const概述:顶层const表示指针本身就是个常量,而底层const表示指针所指的对象是一个常量,如下:
int i = 0;
int *const p1 = &i; // 指向int类型的常指针,指针本身是个常量,无法再指其他,这是顶层const
const int ci = 42;
const int *p2 = &ci; // 指向常int的指针,指针本身不是常量,只是指的地方是,这是底层const
所以以下函数无法重载:
Record lookup(Phone phone);
Record lookup(const Phone phone); // 重复声明了lookup(Phone phone);
Record lookup(Phone *phone);
Record lookup(Phone *const phone); // 重复声明了lookup(Phone *phone);
4)如果形参是某种类型的指针或引用,则通过区分指向的是常量对象还是非常量对象可以实现重载;也就是说对于接受引用或指针的函数来说,对象是常量还是非常量对应的形参是不同的;
所以以下是可以重载的:
Record lookup(Phone &phone); // 该函数作用于Phone的引用
Record lookup(const Phone &phone); // 该函数作用于Phone的常引用
Record lookup(Phone *phone); // 该函数作用于指向Phone的指针
Record lookup(const Phone *phone); // 该函数作用于指向Phone常量对象的指针
2.3 重载函数调用的匹配过程
这一块没有深究,编译器首先根据函数名在就近的作用域寻找,然后找到目标函数后进行类型匹配,如果发现目标函数多余一个,则进行参数匹配,最佳匹配者将获得一次调用机会,要是找不到最佳匹配者,发现有些差不多的(可以进行参数类型转换)的也可以将就一下,要是找不到则报错(所以你会发现和返回值都没啥关系);
3.最后
里面的大部分内容来自参考书,其实我们平时可能不会关注到顶层const相关问题,大家知道函数返回值不能进行函数重载的区分已经解决了好多问题哈哈哈哈;
如有问题,欢迎指正!