c-c笔试面试题目3(编辑修改稿)内容摘要:

C++与 C及其它语言的混合编程。 明白了 C++中 extern C的设立动机,我们下面来具体分析 extern C通常的使用技巧: extern C的惯用法 ( 1) 在 C++中引用 C 语言中的函数和变量,在包含 C 语言头文件(假设为 ) 时 ,需进行下列处理: extern C { # i nclude } 而在 C 语言的头文件中, 对其外部函数只能指定为 extern 类型 , C 语言中不支持 extern C声明 ,在 .c文件中包含了 extern C时会出现编译语法错误。 C++引用 C 函数例子工程中包含的三个文件的源代码如下: /* c 语言头文件 : */ ifndef C_EXAMPLE_H define C_EXAMPLE_H extern int add(int x,int y)。 endif /* c 语言实现文件 : */ # i nclude int add( int x, int y ) { return x + y。 } // c++实现文件,调用 add: extern C { # i nclude } int main(int argc, char* argv[]) { add(2,3)。 return 0。 } 如果 C++调用一个 C语言编写的 .DLL时,当包括 .DLL的头文件或声明 接口函数时,应加 extern C { }。 ( 2) 在 C 中引用 C++语言中的函数和变量时, C++的头文件需添加 extern C,但是在 C 语言中不能直接引用声明了 extern C的该头文件,应该仅将 C文件中将 C++中定义的 extern C函数声明为 extern类型。 C 引用 C++函数例子工程中包含的三个文件的源代码如下: //C++头文件 ifndef CPP_EXAMPLE_H define CPP_EXAMPLE_H extern C int add( int x, int y )。 endif //C++实现文件 # i nclude int add( int x, int y ) { return x + y。 } /* C 实现文件 /* 这样会编译出错:# i nclude */ extern int add( int x, int y )。 int main( int argc, char* argv[] ) { add( 2, 3 )。 return 0。 } 15题目的解答请参考 《 C++中 extern “C” 含义深层探索 》 注解: 16. 关联、聚合 (Aggregation)以及组合 (Composition)的区别。 涉及到 UML 中的一些概念: 关联 是表示两个类的一般性联系,比如 “ 学生 ” 和 “ 老师 ” 就是一种关联关系; 聚合 表示 hasa 的关系,是一种相对松散的关系,聚合类不需要对被聚合类负责,如下图所示,用空的 菱形表示聚合关系: 从实现的角度讲,聚合可以表示为 : class A {...} class B { A* a。 .....} 而 组合 表示 containsa的关系,关联性强于聚合:组合类与被组合类有相同的生命周期,组合类要对被 组合类负责,采用实心的菱形表示组合关系: 实现的形式是 : class A{...} class B{ A a。 ...} 参考文章: ,并简单叙述之。 1. 封装:将客观事物抽象成类,每个类对自身的数据和方法实行 protection(private, protected,public) 2. 继承:广义的继承有三种实现形式:实现继承(指使用基类的属性和方法而无需额外编码的能力)、可视继承(子窗体使用父窗体的外观和实现代码)、接口继承 (仅使用属性和方法,实现滞后到子类实现)。 前两种(类继承)和后一种(对象组合 =接口继承以及纯虚函数)构成了功能复用的两种方式。 3. 多态:是将父对象设置成为和一个或更多的他的子对象相等的技术,赋值之后,父对象就可以根据当前赋值给 它的子对象的特性以不同的方式运作。 简单的说,就是一句话: 允许将子类类型的指针赋值给父类类型的指针。 18. 重载( overload)和重写 (overried,有的书也叫做 “ 覆盖 ” )的区别。 常考的题目。 从定义上来说: 重载 :是指允许存在多个 同名函数 ,而这些函数的 参数表不同 (或许参数个数不同,或许参数类型不同,或许两者都不同)。 重写 :是指子类重新定义复类虚函数的方法。 从实现原理上来说: 重载 : 编译器根据函数不同的参数表,对同名函数的名称做修饰,然后这些同名函数就成了不同的函数(至少对于编译器来说是这样的 )。 如,有两个同名函数: function func(p:integer):integer。 和 function func(p:string):integer。 那么编译器做过修饰后的函数名称可能是这样的: int_func、 str_func。 对于这两个函数的 调用,在编译器间就已经确定了,是 静态 的。 也就是说, 它们的地址在编译期就绑定了(早绑定), 因此, 重载和多态无关。 重写:和多态真正相关。 当子类重新定义了父类的虚函数后,父类指针根据赋给它的不同的子类指针, 动态的调用 属于子类的该函数,这样的函 数调用在编译期间 是无法确定的 (调用的子类的虚函数的地址无法给出)。 因此, 这样的函数地址是在运行期绑定的(晚绑定)。 19. 多态的作用。 主要是两个: 1. 隐藏实现细节,使得代码能够模块化;扩展代码模块,实现代码重用; 2. 接口重用:为了类在继承和派生的时候 ,保证使用家族中任一类的实例的某一属性时的正确调用。 20. Ado 与 的相同与不同。 除 了 “ 能够让应用程序处理存储于 DBMS 中的数据 “ 这一基本相似点外,两者没有太多共同之处。 但是 Ado使用 OLE DB 接口并基于微软的 COM 技术,而 拥 有自己的 接口并且基于微软的 .NET 体系架构。 众所周知 .NET 体系不同于 COM 体系, 接口也就完全不同于 ADO 和 OLE DB 接口,这也就是说 和 ADO是两种数据访问方式。 提供对XML 的支持。 21. New delete 与 malloc free 的联系与区别 ? 答案:都是在堆 (heap)上进行动态的内存操作。 用 malloc 函数需要指定内存分配的字节数并且不能初始化对象, new 会自动调用对象的构造函数。 delete 会调用对象的 destructor,而 free 不会调用对象的 destructor. 22. define DOUBLE(x) x+x , i = 5*DOUBLE(5); i 是多少。 答案: i 为 30。 23. 有哪几种情况只能用 intialization list 而不能用 assignment? 答案:当类中含有 const、 reference 成员变量;基类的构造函数都需要初始化表。 24. C++是不是类型安全的。 答案:不是。 两个不同类型的指针之间可以强制转换(用 reinterpret cast)。 C是类型安全的。 25. main 函数执行以前,还会执行什么代码。 答案:全局对象的构造函数会在 main 函数之前执行。 26. 描述内存分配方式以及它们的区别 ? 1) 从静态存储区域分配。 内存在程序编译的时候就已经分配好,这块内存在程序的整个运行期间都存在。 例如 全局变量, static 变量。 2) 在栈上创建。 在执行函数时, 函数内局部变量的存储单元都可以在栈上创建 ,函数执行结束时这些存储单元自动被释放。 栈内存分配运算内置于处理器的指令集。 3) 从堆上分配 , 亦称动态内存分配。 程序在运行的时候用 malloc 或 new 申请 任意多少的内存,程序员自己负责在何时用 free 或 delete 释放内存。 动态内存的生存期由程序员决定,使用非常灵活,但问题也最多。 和 class 的区别 答案: struct 的成员默认是公有的,而类的成员默认是私有的。 struct 和 class 在其他方面是功能相当的。 从 感情上讲,大多数的开发者感到类和结构有很大的差别。 感觉上结构仅仅象一堆缺乏封装和功能的开放的内存位,而类就象活的并且可靠的社。
阅读剩余 0%
本站所有文章资讯、展示的图片素材等内容均为注册用户上传(部分报媒/平媒内容转载自网络合作媒体),仅供学习参考。 用户通过本站上传、发布的任何内容的知识产权归属用户或原始著作权人所有。如有侵犯您的版权,请联系我们反馈本站将在三个工作日内改正。