1. C++作为面向对象程序设计语言的三大特性包括封装、继承和多态,请写出包含这三
种技术的代码(多态又分静态多态和动态多态)。
答案:
封装:getName(),setName()
继承:Class B: public Class A
多态:
静态多态:函数重载和运算符重载
动态多态:动态绑定,运行时指定。
dum是一个虚函数。父类指针->dump(); 子类指针->dump();
2. 请写出关于函数double f(int * p);的函数指针数组的定义。
答案:
typedef double (*FP)(int * p);
FP f[10];
3. 请写出实现A类类型到B类类型隐式类型转换的代码。
答案:
4. 基类的虚拟析构函数的意义是什么?
答案:派生类的对象通过基类指针删除时,如果基类的析构函数不是虚函数时,其结果为未定义。
5, explicit作用。
答案:在C++中,explicit关键字用来修饰类的构造函数,被修饰的构造函数的类,不能发生相应的隐式类型转换,只能以显示的方式进行类型转换。
explicit使用注意事项:
*explicit 关键字只能用于类内部的构造函数声明上。
*explicit 关键字作用于单个参数的构造函数。
*在C++中,explicit关键字用来修饰类的构造函数,被修饰的构造函数的类,不能发生相应的隐式类型转换。
6. extern C的作用
答案:同样的函数通过C和C++编译后生成的函数名是不一样的。在C++代码中调用用C写成的库文件,就需要用extern "C"来告诉编译器:这是一个用C写成的库文件,请用C的方式来链接它们。很多C语言写成的库中都被extern C给修饰了。
同时extern关键字还可以置于变量或者函数前,以表示变量或者函数的定义在别的文件中,提示编译器遇到此变量和函数时在其他模块中寻找其定义。
7. const修饰指针的用法
const char *ptr , char const * ptr ,因为const在*的左侧,所以修饰char。表明该指针指向一个常量字符。
char * const ptr; 表明该指针是一个常量,必须定义的时候就初始化。
char**p1;char*const*p2=p1;//合法: p1是指向(char *)类型的指针,p2是指向“带有const限定"的(char*)类型的指针。
那就是const修饰的变量,其实质是告诉程序员或编译器该变量为只读,如果程序员在程序中显示的修改一个只读变量,编译器会毫不留情的给出一个error。而对于由于像数组溢出,隐式修改等程序不规范书写造成的运行过程中的修改,编译器是无能为力的,也说明const修饰的变量仍然是具备变量属性的。
8,思考c++和Java的不同之处,比如,Java中的初始化,垃圾回收,接口,异常,虚函数,等等。
9,关于智能指针的介绍
智能指针的实现
10, 构造函数可不可以是虚函数
答案:虚函数的执行是通过虚函数表来实现的,因此这个虚函数表一定要在虚函数调用之前初始化完成。生成一个类的对象要执行构造函数,而设置VPTR也是在构造函数中完成的。其实在虚函数运行之前,对象的类型应该是完全的。而构造函数执行之前,对象的类型是不完全的。如果构造函数也是虚函数的话,那么VPTR就没人来初始化,不完全的类型的对象也无法执行这个虚的构造函数。
11,static函数可不可以是虚函数
静态函数在编译过程中已经完成了函数地址定位,虚函数是运行时期确定的。所以这两个概念是矛盾的。
虚成员函数在执行时可以通过this这个隐藏形参所指对象判断是什么类型的,再通过虚函数表调用正确版本的函数。而static成员函数无this指针。
12,statci函数为什么没有this指针
1)要从C++中函数的实现机制说起了。类的成员函数的实现机制和普通函数没有本质区别,对编译器而言,经过名称处理以后(在函数名前加上命名空间、类名),一个成员函数就是普通函数了,在编译后的代码区域有确定的函数体和入口地址。最大的差别在于发生调用时,对于成员函数,编译器会隐含语句push this,其中this指针指向对象的地址,这就是操作所需要的数据的所在。
2)而静态成员函数实际上就是普通函数,只不过编译器限制了它的名字可视范围而已(因为在编译时在函数名前加上了类名)。因此调用静态成员函数时没有也不需要有push this指针的过程,只需要在函数名字前加上类名限定符就可以了。