C++是基于C语言而形成的一门面向对象的语言,所以C++在完全支持C语言的语法基础上,新增了很多语法。不过有一部分语法是为了解决C语言中存在的诸多不足。
一、命名空间
在C语言中可能会存在这样一种问题 —— 命名冲突,举个例子:
你定义的某个变量名,和C语言某个标准库中的定义重名。如下图所示:

![]()
这种情况下,C语言编译器就会报错,但是命名冲突绝不仅仅是只有这一种情况,当多人编写同一个项目是,A和B在写各自的部分时,很有可能对于不同变量起了相同名字,这在代码合并的时候,也会有命名冲突的问题。
所以C++中为了解决命名冲突的问题,定义了命名空间这种新的语法形式。C语言中有全局域、局部域,而在C++中命名空间也是一种新的域,即命名空间域。当将变量定义在命名空间域时,就可以避免命名冲突的问题。
1.命名空间的定义:
命名空间的定义需要用到namespace关键字,形式如下:

其中test是自定义的该命名空间的名字,在命名空间中不仅可以定义变量,还可以定义函数、类型,甚至是嵌套定义。

此外,同一个工程中,不同的.cpp文件中也可以出现相同名称的命名空间,最后在链接过程会被合并成为一个命名空间。不过需要注意的是,相同名称的命名空间中,如果其成员名称也相同会导致链接失败。
2.命名空间的使用
如果仅仅定义了一个命名空间,不使用特定的方法去访问该命名空间域中的成员时,会导致报错。

想要访问命名空间中的成员,有三种方法,下面依次举例:
(1)全局展开:
关键字using + namespace + 命名空间名

(2)指定展开:
using + 命名空间名 + 域作用限定符:: + 命名空间成员名

(3)指定访问:
命名空间名 + :: + 命名空间成员名

(4)两个问题:
①嵌套的命名空间怎么访问?
运用以上三种方法均可以解决,这里只演示一种。

②全局变量名和命名空间成员名冲突会发生什么?
此时全局变量和命名空间成员可以共存,但是如果不指定访问会访问全局。

可以加域作用限定符来指定访问。

二、C++输入输出
在上一节中演示输出,均使用了C语言中的printf函数,那怎么通过C++的输入输出函数来打印我们想要的内容呢?

除了cout以外,还有标准输入对象cin,和流提取预算符>>,并且C++的输入输出无需像C语言一样限定类型。

通常直接全局展开std的话,可能会有命名冲突的情况,所以这里我采用了另外一种方法去访问标准库std中的成员,当然还有一种方式,大家可以自行尝试。
三、缺省参数
缺省参数在函数声明或定义时,给函数的形参一个默认值,如果未传对应的实参就使用默认值,如果传入了相应的实参就将实参拷贝给形参。
缺省参数分为全缺省和半缺省两种情况:
1.全缺省:

2.半缺省:
半缺省的情况有些特殊,需要从右往左缺省。

最后说明一点,函数的声明和定义中,不能都给缺省参数,会导致重定义。

想解决也很简单,声明给缺省参数,定义就不给。

四、函数重载
函数重载是指同一作用域中的功能类似的同名函数,这些函数的形参类型、数量或者顺序不同,常用来处理功能类似但数据类型不同的问题。

图中很直观的表示出了,ADD这个函数在传入整形和浮点型数据时,调用了不同的函数,这是怎么做到的呢,而在C语言中为什么没有函数重载呢?
1.编译、链接
这里先谈一下C/C++程序是怎么从代码变成计算可以执行的机器指令的。主要有两个大过程:编译、链接,其中编译又分为三个环节:预处理、编译、汇编。接下来简单说一下这几个阶段都分别干了哪些事情(如果想了解详细的请参考其他资料,这里只是简单说明)。
预处理阶段:头文件的包含、注释的删除、#define的替换和删除
编译阶段:语法分析、将C/C++代码翻译成为汇编代码
汇编阶段:将汇编代码翻译为二进制指令、生成符号表
链接阶段:合并段表、符号表的合并和重定位
链接阶段需要依靠汇编阶段生成的符号表去找变量、函数等的地址,这里寻找函数时会依靠函数名修饰规则所规定的修饰后的名字在符号表中寻找,而C/C++就是在函数名修饰规则上有所不同,就使得C不支持函数重载,而C++支持函数重载。
2.构成函数重载的多种形式
①类型不同
上文例子中即是。
②顺序不同

③个数不同

我这里举的例子具有一定的特殊性,首先这肯定是构成函数重载的,但是我给第二个函数一个缺省参数,当出现无参调用时就会出现问题,所以要避免这种情况.
最后说一句,函数重载对函数的返回值没有要求,举例说明:

743

被折叠的 条评论
为什么被折叠?



