当我们想把它数出来时,却发现它无止境的往远跑,因缺乏准确性的特点,和无穷大不是数一样,无理数也不是真正的数。
--------------数学史
1.C++内联函数
- 在函数声明或定义前加关键字inline
注意:程序将函数作为内联函数时,编译器不一定满足这种要求,它可能认为该函数过大或者递归,不将其作为内联函数,内联函数是牺牲内存换取速度的函数,只有一行代码的小型函数适合作为内联函数(经常被调用的化效益更高)。
内联函数和宏的区别是:内联函数依然保持了函数的特性,会计算表达式的值并按值传递。
2.引用变量(C++新增类型)
引用本质是一个指针(对编译器来说,分配内存),对写程序的人来说是已定义变量的别名,它主要用作结构,而不是内置类型。
引用声明时必须初始化,像数组,不全像,这点像哈哈哈哈。
引用的典型用途是作为函数的参数,但有以下注意事项:
2.1实参和引用参数不匹配时,仅当为const引用时(非const编译器将禁止这样做,因为它可能完成不了编程序者的意图,这时将创建临时变量,并让引用变量指向它。)
- 实参类型正确,但不是左值(C++11新增了右值引用,使用&&声明)
- 实参类型不正确,但可以转化为正确的类型
为何要返回引用:
xixi=miss(c);
//如果miss返回一个结构,将把整个结构复制到一个临时的位置,再将这个拷贝到xixi。但返回值为引用时,直接将c复制到xixi,好像指针做不到这点!!!虽然它本质是个指针。。。。
返回引用时避免指向一个临时变量,好的办法是返回参数引用。
string类定义了一种char*到string的转换功能,这使得字符串字面量,以空字符结尾的char数组,或指向char的指针变量可以传递进string类型参数
基类引用可以指向派生类而无需进行强制类型转换。
3.默认参数
带参列表函数从右向左添加默认值,只有原型指定了默认值,函数定义和没有默认参数时完全相同。
4.函数重载
函数重载的关键是函数的特征标。
- 当函数重载和默认参数重合时将视为错误
- 当实参有多个类型转换方式时将视为错误
- 编译器在检查函数特征标时,将把类型引用和类型本身视为一个特征标
名称修饰:C++编译器跟踪函数的方式,将函数原型转化为不太好看的内部表示,以描述该接口。
5.函数模板
C++新增特性,将类型作为参数传递给模板,可使编译器生成该函数。
模板并不创建任何函数,最终的代码不包括任何模板,只包含实际函数,它只是告诉编译器如何定义函数。
隐式实例化
显式实例化 template void swap<int>(int,int); 声明的话不管用不用都通过模板生成定义不声明的话间接使用,有显式就不要隐式了
显式具体化 template<> void swap<int>(int&,int&)
6.编译器选择哪个函数版本
- 创建候选函数列表
- 使用候选函数列表创建可行性函数列表
- 确定最佳的可行性函数
匹配最佳到最差的顺序:
- 完全匹配(允许一些无关紧要的转换如type到type&)
- 提升转换(char和short到int,float到double);
- 标准转换(int到char,long到double);
- 用户自定义转换;
有多个原型匹配且不矛盾时:
- 非const指针和应用优先和非const指针和引用结合。
- 有多个模板函数函数适合,则选择更具体的,如果都不具体,则是是不确定的即错误的。
7.类型推断
类型是值域且附加其上一系列特定操作。
关键字decltype(C++11)
提供的参数可以是表达式。
无法预先知道类型情况下,使用后置返回类型,使用完参数后再返回类型。
template<typename T>
auto xixi(T c) -> decltype(c)
其中auto是一个占位符,表示后置返回类型,C++11给auto新增的一种角色。