经过许久的C语言学习,前不久终于开始了c++的学习经过总结写下了这篇文章.
总结:C++总计63个关键字,C语言32个关键字
废话少说直接开始第一个知识点
首先按照学习一门语言的惯例写一段 Hello world 入门代码.
刚开始学能你不清楚为什么我只打印一句 Hello world 包含头文件我理解但为啥还要带一句 using namespace std 。有人可能表示这是命名空间书上说过,对大致上可以这么理解。
但是你知道他为啥要这么定义吗?定义规则是什么吗?自己该如何定义吗?
如果都知道,很高兴的和你说您可以跳过本篇这个知识点了
一个组,一起开发一个大型项目。但是他们但他们编写程序时就可能出现重名的函数,变量,结构体等,合并时就出现问题了大量的命名冲突。最初,人们就想了个办法,将名字取得更长更复杂来避免重复,可这样做却给编写和阅读带来了困难。后来,人们创造了命名空间这个概念,它能有效地指出某个标示符到底属于哪个库。
定义命名空间,需要使用到namespace 关键字,后面跟命名空间的名字,然后接一对{ }即可,{ }中即为命名空间的成员。
如下 zgb 是命名空间的名字,大括号中的 sum 变量和 Add 函数及结构体 book 是 zgb 空间的成员。
namespace zgb
{
int sum = 10;
int Add(int x, int y)
{
return x + y;
}
struct book
{
char name[15];
}mm;
}
可如下嵌套定义命名空间
namespace binbang
{
int a = 29;
namespace binbin
{
int Add(int x, int y)
{
return x + y;
}
}
}
命名空间相同时如相互的成员名均不同则会合并相同的命名空间,但成员名相同时则会发生命名冲突从而报错。
总结:
1:命名空间中可以定义变量,函数,结构体等非常自由。
2:命名空间可以嵌套定义
3:注意若同一工程中,命名空间名字如果相同,相同空间名中的成员会合并为一个命名空间,但这就丧失了命名空间的作用,因为由于是合并而成的里面的命名可能冲突导致报错
4:只要命名空间名字不同,每个命名空间是互不干扰的就像局部变量一样
命名空间的使用有三种方式:
使用方法:命名空间名 : : 该空间成员(变量函数结构体等),符号左边写命名空间名,右边写该该空间成员
举例如下:
嵌套时也是如图加作用域限定符即可
学会了使用现在咱验证一下不同命名空间中同名变量是否会冲突,答案是不会。如图
使用方法:using 命名空间名 : : 该空间成员
如下图, using bb::sum;等于是声明了 bb 中的变量 sum,后面可以不加作用域限定符即可直接使用。注意如果该语句在全局中则该声明全局有效,如该语句在局部则该声明局部有效。
使用方法:using namespace 命名空间名称
作用:将该空间所有成员引入,如下面using namespace std,就是将命名空间 std 中的内容全部展开(声明/引入),其中就包括了cout 。所以可以之后cout可以直接使用;
注意:该命令如在全局中使用,那将使命名空间失去意义,如果全局中与 引入(声明/展开)成员同名的变量或函数等将发生冲突,不同命名空间均在全局或同一个局部空间使用using namespace 将该空间所有成员引入(声明/展开)时也可能发生冲突。
using namespace,一般在刷题,测试及局部中使用比较合适,工程和全局中可控性太低
缺省参数是声明或定义函数时为函数的参数指定一个缺省值。在调用该函数时,如果没有指定实参则采用该形参的缺省值,否则使用指定的实参。
如下图,test7 函数中有一个缺省值 x = 10,当调用 test7 函数时传参为22则,x 等于22。当调用 test7 函数时参数为空则 x 默认等于缺省值10;
概念:指函数的参数均为均有缺省值
如下
void test9(int x = 10, int y = 20, int z = 30)
{
cout << x << endl;
cout << y << endl;
cout << z << endl;
}
概念:指函数的部分参数有缺省值,注意参数必须从右往左连续缺省,简要记无缺省值参数不能在缺省值参数的右边。
如下是半缺省参数函数
void test9(int x , int y = 20, int z = 30)
{
cout << x << endl;
cout << y << endl;
cout << z << endl;
}
为啥说无缺省值参数不能在缺省值参数的右边呢?
如下无缺省值参数出现在缺省值参数的右边,程序直接报错了。因为函数传参时是从左到右一 一对应的不能跳过中间参数进行传参,所以没有缺省值的参数需要在右边并且连续,达到优先及易区分等目的。
在实际使用中.c文件中的函数须在.h中声明时,如果要声明的函数带缺省值,应在.h文件中给缺省值,定义函数时不用给缺省值,如果两个都给缺省值那编译器将会报错,因为不知道该用那个
如下编译器将会报错
//a.h (.h文件)
void zgb(int a = 10);
// a.cpp (.cpp文件)
void zgb(int a = 20)
{}
因为声明都没有缺省值那,函数的缺省值又从何而来呢
正确方式
//a.h (.h文件)
void zgb(int a = 10);
// a.cpp (.cpp文件)
void zgb(int a )
{}
总结:
函数重载:是函数的一种特殊情况,C++允许在同一作用域中声明几个功能类似的同名函数,这些同名函数的形参列表(参数个数 或 类型 或 类型顺序)不同,常用来处理实现功能类似数据类型不同的问题。
如下函数同名,但函数参数类型不同,如下当函数调用时传参为int 类型则会调用函数参数为int类型的Add函数,反之则调用参数为double类型的Add函数;
//函数重载
int Add(int x, int y)
{
cout << "Add(int x, int y)" << endl;
return x + y;
}
double Add(double x, double y)
{
cout << "Add(double x, double y)" << endl;
return x + y;
}
void tese2()//函数重载,函数参数类型不同
{
Add(1, 2);//编译时就链接好了对应函数
Add(1.3, 1.5);
}
如下函数同名,但函数参数个数不同,如下当函数调用时只传一个参数则使用一个参数Add函数,当函数调用时传两个参数则使用两个参数Add函数。(当然传参与函数参数需相同)
int Add( int y, char x)
{
cout << "Add( int y, char x)" << endl;
return y;
}
int Add(int x)
{
cout << "Add(int x)" << endl;
return x;
}
void tese4()//函数重载,函数参数个数不同
{
Add(1);
Add(2, 4);
}
如下函数同名,但函数各参数类型顺序不同,如下当调用函数传参时参数1为 char 类型参数二为 int 类型,则会调用 int Add(char x, int y)
当调用函数传参时参数1为 int 类型参数二为 char 类型,则会调用 int Add( int y, char x)
int Add(char x, int y)
{
cout << "Add(char x, int y)" << endl;
return x;
}
int Add( int y, char x)
{
cout << "Add( int y, char x)" << endl;
return y;
}
void tese3()//函数重载,函数参数顺序不同
{
Add('a', 1);
Add(1, 'a');
}
1:为什么C++支持函数重载,而C语言不支持函数重载呢?
在C/C++中,一个程序要运行起来,需要经历以下几个阶段:预处理、编译、汇编、链接。
首先看看采用C语言编译器编译后结果,如下图在linux下,采用gcc编译完成后,函数名字的修饰没有发生改变。
在看看采用c++编译器编译后的结果,如下图在linux下,采用g++编译完成后,除main函数外的函数名字的修饰发生改变,编译器将函数参数类型信息添加到修改后的名字中。
由于Windows下Vs编译时函数的修饰规则较为复杂还是直接看下图吧
对比Linux会发现,windows下vs编译器对函数名字修饰规则相对复杂难懂,但道理都是类似的,我们就不做细致的研究了。
C++入门第一期内容就这些了,下期会更新引用/内联函数/auot等