1、结构体
在C语言中,结构体不能包含函数;C++的结构体可以包含函数。
在C++语言中,结构体是用关键字struct声明的类。结构体默认情况下,其成员是公有的(public);类默认情况下,其成员是私有的(private)。
2、类与对象
类的对象若没有进行初始化,则对象中的成员变量在相应的在内存空间中的值是一个随机值。
3、构造函数
C++,如果一个类没有提供任何的构造函数,则C++提供一个默认的构造函数(由C++编译器提供),这个默认的构造函数是一个不带参数的构造函数,它只负责创建对象,而不做任何的初始化工作。只要一个类定义了一个构造函数,不管这个构造函数是否是带参数的构造函数,C++就不再提供默认的构造函数。也就是说,如果为一个类定义了一个带参数的构造函数,还想要无参数的构造函数,则必须自己定义。
4、析构函数
析构函数不允许有返回值,且不允许带参数,一个类中只能有一个析构函数。
注意: 在类中定义成员变量时,不能直接给成员变量赋初值。例如:
class point
{
int x = 0; // 错误,此处不能给变量x赋值
int y;
}
5、函数的重载(overload)
重载构成的条件:函数的参数类型、参数个数不同,才能构成函数重载。
注意:只有函数的返回类型不同是不能构成函数的重载的。
6、this指针
对象调用成员函数时,成员函数除了接收实参外,还接收该对象的地址,这个地址被隐含的形参this指针所获取,等价于this = &object。
7、子类中调用父类的带参数的构造函数
例:
fish(): animal(400, 300)
{
.........
}
即:在fish类的构造函数后,加一个冒号(:),然后加上父类的带参数的构造函数。这样,在子类的构造函数被调用时,系统会先去调用父类的带参数的构造函数去构造对象。这种初始化方法,还常用来对类中的常量(const)成员进行初始化。例如:
class point
{
public:
point():x(0), y(0){...}
private:
const int x;
const int y;
}
当然类中的普通成员变量也可以采取此种方式进行初始化,然而,这就没有必要了。
8、类的继承及类中成员的访问特性
基类的访问特性 | 类的继承特性 | 子类的访问特性 |
Public | Public | Public |
Public | Protected | Protected |
Public | Private | Private |
9、多重继承
初始化顺序是按照基类表中的说明顺序进行初始化的。
10、虚函数与多态性
当C++编译器在编译的时候,发现Animal类的breathe()函数是虚函数,这个时候C++就会采用迟绑定(late binding)的技术,在运行时,依据对象的类型(在程序中,我们传递的Fish类对象的地址)来确认调用的哪一个函数,这种能力就做C++的多态性。没有在breath()函数前加virtual关键字时,C++编译器在编译时就确定了哪个函数被调用,这叫做早期绑定(early binding)。
C++的多态性用一句话概括就是:在基类的函数前加上virtual关键字,在派生类中重写该函数,运行时将会根据对象的实际类型来调用相应的函数。
注意:virtual在声明时要添加,定义实现时就不需要加virtual了。(否则会报编译错误)
11、纯虚函数
virtual void breathe() = 0;
纯虚函数是指被标明不具体实现的虚函数(纯虚函数也可以有函数体,但这种提供函数体的用法很少见)。
凡是含有纯虚函数的类叫做抽象类。这种类不能声明对象,只是作为基类为派生类服务。
12、函数的覆盖(override)
构成覆盖的条件:
基类函数必须是虚函数(使用virtual关键字进行声明)。
发生覆盖的两个函数要分别位于派生类和基类中。
函数名称和参数列表必须完全相同。
说明:由于C++的多态性是通过虚函数来实现的,所以函数的覆盖总是和多态性关联在一起。在函数覆盖的情况下,编译器会在运行时根据对象的实际类型来确定要调用的函数。
13、函数的隐藏
所谓隐藏,是指派生类中具有与基类同名的函数(不考虑参数列表是否相同),从而在派生类中隐藏了基类的同名函数。
函数隐藏的情况:
(1)派生类的函数与基类的函数完全相同(函数名和参数列表都相同),只是基类的函数没有使用virtual关键字。此时基类的函数将被隐藏,而不是覆盖。(与覆盖进行比较)
(2)派生类的函数与基类的函数同名,但参数列表不同,在这种情况下,不管基类的函数是否有virtual关键字,基类的函数都将被隐藏。(注意这种情况与函数重载的区别,重载发生在同一个类中)
区分覆盖和隐藏的方法:函数的覆盖是发生在派生类与基类之间,两个函数必须完全相同,并且都是虚函数。那么不属于这种情况的,就是隐藏了。
当隐藏发生时,如果在派生类的同名想要调用基类的被隐藏函数,可以使用“基类名::函数名(参数)”的语法形式。
14、引用
引用就是一个变量的别名,它需要用另一个变量或对象来初始化自身。例:
int a = 5;
int& b= a; //用&表示申明一个引用。引用必须在申明时进行初始化
15、作用域标识符
::叫做作用域标识符,用于指明一个函数属于哪个类或一个数据属于哪个类。::前面如果不跟类名,表示全局函数(即非成员函数)或全局数据
16、在包含头文件时,<>和“”的区别:<>和“”表示编译器在搜索头文件时的顺序不同,<>表示从系统目录下开始搜索,然后再搜索PATH环境变量所列出的目录,不搜索当前目录;“”表示先从当前目录搜索,然后是系统目录和PATH环境变量所列出的目录。所以如果我们知道头文件在系统目录下,就可以直接用<>,这样可以加快搜索速度。