目录
1.C++的第一个程序
2.c++历代版本
3.命名空间
3.1 namespace关键字
namespace的用法:
namespace中定义函数
namespace中定义结构体
C++中的域:
3.2就近原则
4.命名空间的使用
5.C++输入输出
6.缺省参数
全缺省:
半缺省:必须从右往左连续缺省(也就是给一个参数设定缺省值后,该参数后面的都必须有缺省值)
7.函数重载
(1).参数类型不同
(2).参数个数不同
(3).参数顺序不同:
(4).疑惑点:
当缺省函数和无参函数重载时:
返回值不同不构成重载
8.引用
8.1引用的特点:
(1).引用在定义时必须初始化
(2).一个变量可以有多个引用
(3).引用一旦引用一个实体,再不能引用其他实体
8.2const引用
8.2.1权限放大问题
8.2.2权限缩小问题
8.2.3对常量的引用
8.2.4隐式类型转换的引用
9.指针和引用的关系
1.C++的第一个程序
C++兼容C语言大多数的语法,所以C语言实现的helloworld依然可以运行,C++中需要把定义文件代码的后缀改为.cpp,visualstudio编译器看到是.cpp就会调用C++编译器编译,linux下要用g++编译,不再是gcc(c语言编译器)。
#include<iostream>
using namespace std;int main()
{cout << "hello world" << endl;//<< :流输出运算符return 0;
}
2.c++历代版本
C++98 C++11 C++20 为主流大版本
3.命名空间
3.1 namespace关键字
namespace的用法:
定义一个命名空间,需要namespace关键字,后面跟上命名空间的名字,然后再跟一对{}即可, {}中为命名空间的成员。命名空间中可以定义 变量,函数,类型等。
C语言中有命名冲突,当我们在写一个c语言程序时,比如我们定义了一个int rand=10;这个变量,如果我们没有包含#include<stdlib.h>这个头文件时,可以通过编译,但是我们包含了这个头文件,就会报错rand重定义,这是因为#include<stdlib.h>中还有一个rand()函数,所以会报错重定义。
为解决命名冲突,就要用到namespace命名空间。C++标准库的命名空间为std。
例如:
要使用域作用限定符(::),左边写上命名空间的名字,右边写命名空间成员。
namespace 实质是定义出了一个域,这个域和全局的域各自独立,不同的域可以定义同名变量,所以rand就不会再冲突了。
namespace中定义函数
#include<iostream>
#include<stdlib.h>
using namespace std;
namespace mike
{int rand = 100;int gcd(int a, int b){return b == 0 ? a : gcd(b, a % b);}}
int main()
{int a = 10;int b = 20;cout <<mike:: gcd(a, b) << endl;return 0;
}
namespace中定义结构体
#include<iostream>
#include<stdlib.h>
using namespace std;
namespace mike
{int rand = 100;struct test{int a = 666;};}
int main()
{struct mike::test p1;return 0;
}
C++中的域:
C++域中有函数局部域,全局域,命名空间域,类域。
3.2就近原则
当全局中和局部中有同名变量时,优先输出局部变量,因为编译器查找是从局部到全局。
#include<iostream>
#include<stdlib.h>
using namespace std;int a = 10;
int main()
{int a = 100;cout << a << endl;//输出结果为100return 0;
}
但是如何此时如何访问全局的a呢?
要使用 域作用限定符(::)
域作用限定符左边什么都不写,默认是全局域。
#include<iostream>
#include<stdlib.h>
using namespace std;int a = 10;
int main()
{int a = 100;cout << ::a << endl;//输出结果为10return 0;
}
4.命名空间的使用
(1).指定命名空间访问,项目中推荐这种用法。
(2).using将命名空间中某个成员展开,项目中经常访问的且不存在冲突的成员推荐这种方式。
(3).展开命名空间中全部成员,在项目中不推荐,冲突风险大,只有在日常练习中才使用。
#include<iostream>
#include<stdlib.h>
namespace mike
{int rand = 100;int ou = 1000;
}
using mike::rand;//展开指定成员,方法(2)
using namespace mike;//展开命名空间中全部成员 方法(3)int main()
{return 0;
}
5.C++输入输出
(1)<iostream>是Input Output Stream的缩写,是标准的输出输出流库。
(2).std::cin是istream类的对象,std::out是ostream类的对象。
(3).std::endl是一个函数,流输出时,相当于插入了一个换行字符。
(4).<<是流插入运算符,>>是流提取运算符。
(5).C++的输入输出可以自动识别变量类型(本质是通过函数重载实现的)。
6.缺省参数
(1).缺省参数是声明或定义函数时为函数的参数指定一个缺省值。在调用该函数时,如果没有指定实参
则采用该形参的缺省值,否则使用指定的实参,缺省参数分为全缺省和半缺省参数。(2).全缺省就是全部形参给缺省值,半缺省就是部分形参给缺省值。C++规定半缺省参数必须从右往左依次连续缺省,不能间隔跳跃给缺省值。
(3).带缺省参数的函数调用,C++规定必须从左到右依次给实参,不能跳跃给实参。
(4).函数声明和定义分离时,缺省参数不能在函数声明和定义中同时出现,规定必须函数声明给缺省值。
例如:
#include<iostream>
#include<stdlib.h>
using namespace std;void test(int a = 0)
{cout << a << endl;
}
int main()
{test();test(666);return 0;
}
输出结果:
全缺省:
#include<iostream>
#include<stdlib.h>
using namespace std;void test1(int a = 100, int b = 200, int c = 300)//全缺省
{cout << "A "<<a << ' ' <<"B " <<b << ' ' <<"C "<< c << endl;
}int main()
{test1();test1(1);test1(1,2);//必须从左向右依次给参数return 0;
}
半缺省:
必须从右往左连续缺省(也就是给一个参数设定缺省值后,该参数后面的都必须有缺省值)
#include<iostream>
#include<stdlib.h>
using namespace std;
void test1(int a , int b = 200, int c=300)//半缺省,必须从右往左连续缺省
{cout << "A " << a << ' ' << "B " << b << ' ' << "C " << c << endl;
}int main()
{test1();return 0;
}
7.函数重载
C++支持在同一作用域中出现同名函数,但是要求这些同名函数的形参不同,可以是参数个数不同或者类型不同。这样C++函数调用就表现出了多态行为,使用更灵活。C语言是不支持同一作用域中出现同名函数的。
(1).参数类型不同
#include<iostream>
#include<stdlib.h>
using namespace std;
//参数类型不同
void test(int a, int b)
{cout << "test(int a, int b)" << endl;
}
void test(double a, double b)
{cout << "test(double a, double b)" << endl;
}
void test(int a, double b)
{cout << "test(int a, double b)" << endl;
}
int main()
{test(1, 1);test(2.2, 2.2);test(1, 2.2);return 0;
}
运行结果:
(2).参数个数不同
#include<iostream>
#include<stdlib.h>
using namespace std;
//参数个数不同
void test()
{cout << "test()" << endl;
}
void test(int a)
{cout << "test(int a)" << endl;
}int main()
{test();test(1);return 0;
}
运行结果:
(3).参数顺序不同:
#include<iostream>
#include<stdlib.h>
using namespace std;
//参数顺序不同
void test(int a,char c)
{cout << "test(int a,char c)" << endl;
}
void test(char c, int a)
{cout << "test(char c, int a)" << endl;
}
int main()
{test(1,'c');test('c',1);return 0;
}
运行结果:
(4).疑惑点:
当缺省函数和无参函数重载时:
#include<iostream>
#include<stdlib.h>
using namespace std;//这两个函数也构成重载,但是调用test()时会报错,存在调用歧义,不知道应该调用那个
void test()
{cout << "test()" << endl;
}
void test(int a = 1)
{cout << "test(int a = 1)" << endl;
}int main()
{test();return 0;
}
报错:
返回值不同不构成重载
#include<iostream>
#include<stdlib.h>
using namespace std;void test()
{cout << "void test()" << endl;
}
int test()
{cout << "int test()" << endl;return 0;
}int main()
{return 0;
}
报错:
8.引用
引用不是新定义一个变量,而是给已存在变量取了一个别名,编译器不会为引用变量开辟内存空间,它和它引用的变量共用同一块内存空间。
语法:类型& 引用别名 = 引用对象;
例1:
#include<iostream>
#include<stdlib.h>
using namespace std;int main()
{int a = 0;int& b = a;int& d = b;++d;cout <<"A="<< a <<" B="<< b << " D="<<d << endl;return 0;
}
运行结果:
例2:
#include<iostream>
#include<stdlib.h>
using namespace std;void swap(int& a, int& b)
{int c = a;a = b;b = c;
}
int main()
{int a = 666;int b = 0;cout << "A=" << a << ' ' << "B=" << b << endl;swap(a, b);cout << "A=" << a << ' ' << "B=" << b << endl;return 0;
}
运行结果:
8.1引用的特点:
(1).引用在定义时必须初始化
(2).一个变量可以有多个引用
(3).引用一旦引用一个实体,再不能引用其他实体
(1).引用在定义时必须初始化
int main()
{int a = 10;int& b;return 0;
}
报错:
(2).一个变量可以有多个引用
int main()
{int a = 10;int& b = a;int& c = b;return 0;
}
(3).引用一旦引用一个实体,再不能引用其他实体
int main()
{int a = 10, b = 20;int& c = a;c = b;//只是把b的值赋值给c,不是将c指向breturn 0;
}
8.2const引用
8.2.1权限放大问题
int main()
{const int a = 10;//a只可读不可写int& b = a;//b这个别名即可写又可读,所以会报错,这个问题叫做权限放大return 0;
}
报错:
正确:
int main()
{const int a = 10;//a只可读不可写const int& b = a;//b这个别名即可写又可读,所以会报错,这个问题叫做权限放大return 0;
}
8.2.2权限缩小问题
int main()
{int a = 10;//a即可读又可写const int& b = a;//b这个别名只允许读,不允许写,这样叫权限缩小,权限缩小没有任何问题return 0;
}
综上所述,权限可以缩小,但不可以放大
8.2.3对常量的引用
对常量引用只有const引用才可以。同时因为表达式为临时常量,临时常量具有常性,也必须使用const引用。
int main()
{int& a = 10;return 0;
}
报错:
const引用:
int main()
{const int& a = 10;int b = 10, c = 20;const int& d = (b + c);return 0;
}
8.2.4隐式类型转换的引用
int main()
{double a = 3.14;int& b = a;return 0;
}
报错:
必须使用const引用
因为在隐式类型转换时会产生临时对象,临时对象具有常性,必须使用const引用。
int main()
{double a = 3.14;const int& b = a;return 0;
}
9.指针和引用的关系
(1).上引用是一个变量的取别名不开空间,指针是存储一个变量地址,要开空间。
(2).引用在定义时必须初始化,指针建议初始化,但是语法上不是必须的。
(3).引用在初始化时引用一个对象后,就不能再引用其他对象;而指针可以在不断地改变指向对象。
(4).引用可以直接访问指向对象,指针需要解引用才是访问指向对象。
(5).sizeof中含义不同,引用结果为引用类型的大小,但指针始终是地址空间所占字节个数。
(6).指针很容易出现空指针和野指针的问题,引用很少出现,引用使用起来相对更安全。
本篇完