首页 > 编程 > C++ > 正文

C++笔、面试常见题之一二

2019-11-08 02:45:51
字体:
来源:转载
供稿:网友

我们一定要坚信,在坚持中才能看到希望,而不是看到希望后才开始坚持

Q1:问请用简单语句告诉我C++是什么?

C++是在C语言的基础上开发的一种面向对象编程语言,应用广泛。C++融合了3种不同的编程方式:C语言代表的过程性语言、C++在C语言基础上添加的类代表的面向对象语言、C++模板支持的泛型编程。其编程领域众广,常用于系统开发、引擎开发等应用领域,是最受广大程序员受用的最强大编程语言之一,支持类及继承、封装和多态等特性

Q2:C和C++的区别?

C++在C的基础上增添类,C是一个结构化语言,它的重点在于算法和数据结构。C程序的设计首要考虑的是如何通过一个过程,对输入(或环境条件)进行运算处理得到输出(或实现过程(事务)控制)。而对于C++,首要考虑的是如何构造一个对象模型,让这个模型能够契合与之对应的问题域,这样就可以通过获取对象的状态信息得到输出或实现过程(事务)控制。

Q3:什么是面向对象(OOP)?

面向对象是一种对现实世界理解和抽象的方法、思想,通过将需求要素等转化为对象进行问题处理的思想。 用一张图展示就是: 图片

Q3:指针和引用的区别?

序 号 描述 指针 引用
1 定义 是一个变量,存储的是一个内存地址 变量的别名
2 初始化 可以为空值 不可以为空值,且必须初始化
3 多级 可以多级 只能一级
4 改变值 初始化后可以改变,即指向其他的存储单元 初始化后不可以再改变
5 sizeof 得到的是指针本身的大小 所指向的变量的大小
6 内存分配 指针需要分配内存空间 引用不需要分配
7 解引用 指针需要解引用 引用无需解引用

注:解引用就可以理解为“解码”的意思。假设ptr里面存放的是一个内存地址,那么 * ptr就是这个内存地址里面存放的数据。前面这个“* ”的解引用操作,就可以理解为对这个ptr进行解码,解码得到的数据就是* ptr,也就是我们常说的“这个内存地址里面存放的数据”或者“这个指针指向的数据”。“指针”的理解模式太容易混淆,而“解码”的理解模式更好记一点。

Q4:const在函数中可以作用在哪些地方,意义分别是啥?

const int num(int x);代表num函数的返回值是int类型的常量 int num(int x) const;代表的num函数不能隐形的修改参数x的值 int num(const int x);代表参数x是常量,不可以修改

Q5:new/delete 和 malloc/free 的区别?

相同点:都是申请内存和释放内存 本质区别:malloc/free是C/C++ 语言的标准库函数,new/delete是C++的运算符。 对于用户自定义的对象而言,用malloc/free无法满足动态管理对象的要求。对象在创建的同时要自动执行构造函数,对象在消亡之前要自动执行析构函数。由于malloc/free是库函数不是运算符,不在编译器的控制范围之内,不能够把执行构造函数和析构函数的任务强加给malloc/free,因此C++需要一个能完成动态内存分配和初始化工作的运算符new,以及一个能完成清理和释放内存工作的运算符delete。 联系:C++程序要经常调用C函数,而C程序只能调用malloc/free管理动态内存。因此两者要共存。

Q6:友元的作用?

友元分为友元类和友元函数。 特点:是一种定义在类外部的普通函数或者类,但他需要在类内部进行说明。为了和类的成员函数进行区分,在说明的前面加以 friend关键字。友元不是成员函数,但是他可以访问类的私有成员。友元的作用是提高程序的运行效率,但是他破坏了程序的封装性和隐藏性。使得非成员函数可以方位类的私有成员。

Q7:虚析构函数的作用?

一般情况下,类的析构函数里面都是释放内存资源,而析构函数不被调用的话,就会发生内存泄漏。当然并不是把所有的析构函数都写成虚析构函数,因为当类里面有虚函数的时候,编译器会给类添加一个虚函数表,里面用来存放虚函数的指针,从而增加的类的空间。所有只有当类为基类时,才将析构函数写成虚析构函数。

Q8:虚继承的作用?

基本原则是在内存中只有基类成员的一份拷贝。这样通过把基类继承声明为虚拟的,就只能继承基类的一份拷贝,从而消除歧义。 class A : virtual class B{ };

Q9:宏定义的特点和实现,内联函数取代他的意义

宏定义在形式和使用上像一个函数,但他使用预处理器实现,没有了参数压栈、代码生成等一系列操作。因此效率很高。 虽然效率高,但是是在预处理器中实现的,所以不能进行参数的有效检测,也就不能享受C++编译器严格类型检查的好处,另外返回值也不能强制转换成可转换的合适的类型。 C++中引入了类和类的访问控制,这样如果一个表达式涉及到类的保护成员或者私有成员,就不能用宏定义来实现。 正因为如此,引入了内联函数。内联函数的代码被放入到符号表中,在使用时直接进行替换,没有了展开的开销,效率也很高。 类的内联函数也是一个真正的函数,编译器在调用一个内联函数时,会首先检查他的参数类型,保证调用正确。消除了隐患和局限性。 内敛函数可以作为某个类的成员函数,当然就可以在其中使用所在类的保护成员及私有成员。 内敛函数一般只会用在函数内容比较简单的时候,这样,函数的代码会在任何调用他的地方展开。内联函数最重要的使用地方是:类的存取函数。

Q10:Qt的垃圾回收机制

Qt是以对象树的形式来实现对垃圾的收集。所有继承自QOBJECT类的类,在new的时候就指定了父亲,那么在父亲delete的时候,他也被清理delete。

Q11:Qt信号槽的简单实现原理?

整个原理是比较复杂的,这里只做简单介绍,有兴趣童鞋可搜索细节

在预编译时,保存信号函数和槽函数的索引为字符串,通过宏定义来实现。 建立链接,就是讲信号索引字符串和槽函数索引字符串保存在map中,建立Key-Value的关系 当信号函数触发后,先去找字符串索引,然后再去找map值,然后找到槽函数索引字符串,然后再在分支语句中找到槽函数。至此实现,哈哈,这些可以忽悠一下了,不过细节还需准备为好。

Q12:线程和进程的区别?

进程是程序的一次执行;线程是进程的执行单元。 进程间是独立的,这表现在内存空间、上下环境。线程运行在进程中。 一般来讲,进程无法突破进程边界存取其他进程内的存储空间;而同一进程所产生的线程共享内存空间。 同一进程中的两段代码不能同时进行;除非引入多线程。
发表评论 共有条评论
用户名: 密码:
验证码: 匿名发表

图片精选