函数重载(Overload)
- 规则
- 函数名相同
- 参数个数不同、参数类型不同、参数顺序不同
- 注意
- 返回值类型与函数重载无关
- 调用函数时,实参的隐式类型转换可能会产生二义性
- 本质
- 采用了name mangling 或者 name decoration
- C++编译器默认会对符号名(比如函数名)进行改编、修饰
- 重载时会生成多个不同的函数名,不同编译器(MSVC、g++)有不同的生成规则
- 通过IDA打开【VS_Release——禁止优化】可以看到
示例:以下构成函数重载
参数个数不同
int sum(int a, int b){ return a + b; } int sum(int a, int b, int c){ return a + b + c; }
参数类型不同
int sum(int a, int b){ return a + b; } double sum(double a, double b){ return a + b; }
参数顺序不同
void display(int a, double b){ cout << "int a = " << a << "double b = " << b << endl; } void display(double a, int b){ cout << "double a = " << a << "int b = " << b << endl; }
示例:以下不构成函数重载
返回值类型不同,不构成重载
int sum(int a){ return a + 1; } void sum(int a){ cout << "void sum(int a) " << endl; }
实参的隐式转换,产生二义性
void display(long a){ cout << " void display(long a) " << endl; } void display(double a){ cout << " void display(double a) " << endl; }
默认参数
- C++允许函数设置默认参数,在调用时可以根据情况省略实参。规则如下:
- 默认参数只能按照右到左的顺序
- 如果函数同时有声明、实现,默认参数只能放在函数声明中
- 默认参数的值可以是常量、全局符号(全局变量、函数名)
int age = 33; void test(){ cout << " test() " << endl; } void display(int a = 11, int b = 22, int c = age, void(*func)() = test) { cout << "a = " << a << endl; cout << "b = " << b << endl; cout << "c = " << c << endl; func(); }
函数重载与默认参数可能会产生二义性(建议优先选择使用默认参数)
void display(int a, int b = 20){ cout << "a = " << a << endl; } void display(int a){ cout << "a = " << a << endl; }
内联函数(inline function)
- 使用inline修饰函数的声明或者实现,可以使其变成内联函数
建议声明和实现都加inline修饰
- 特点
- 编译器会将函数调用直接展开为函数体代码
- 可以减少函数调用的开销
- 会增大代码体积
- 注意
- 尽量不要内联超过10行代码的函数
- 有些函数即使声明为inline,也不一定会被编译器内联,比如递归函数
VS 可以在Release模式下禁止编译器内联行为:右击sln --> 属性 --> 配置属性 --> C/C++ --> 优化 --> 优化(已禁用(/Od))
内联函数与宏的比较
- 都可以减少函数调用的开销
- 对比宏,内联函数多了语法检测和函数特性