66. 请说明 fork(),vfork() 的作用,以及两者的区别。

fork() 函数用于创建一个新的进程,新进程是原进程的一个副本,但是有自己的进程 ID。vfork() 函数也用于创建一个新的进程,但是新进程和原进程共享内存空间,直到新进程调用 exec() 函数或者 exit() 函数为止。

两者的区别在于 vfork() 创建的子进程与父进程共享内存空间,因此在子进程中对共享内存的修改会影响到父进程。

67. exit、_exit、_Exit 三者区别,请说明。

exit() 函数用于正常终止一个进程,并返回一个状态码给父进程。_exit() 函数也用于正常终止一个进程,但是不会执行任何清理工作,而是直接退出。_Exit() 函数与 _exit() 函数类似,但是它会执行一些清理工作,比如关闭文件描述符等。

68. Makefile 中 .PHONY 的作用?

.PHONY 是 Makefile 中的一个特殊目标,用于声明一个规则是“伪目标”,即不代表一个真实的文件。这样一来,在执行 make 命令时,无论目标文件是否存在,都会执行该规则。主要用于定义一些不产生文件的规则,比如 clean、install 等。

69. #include <FileName.h> 和 #include "FileName.h" 有什么区别?

#include <FileName.h> 是用于包含系统头文件,编译器会在标准系统目录中查找该文件。而 #include "FileName.h" 是用于包含用户自定义的头文件,编译器会在当前目录中查找该文件。

70. 数组和链表有哪些区别?

数组是一种线性数据结构,它由相同类型的元素按顺序存储在连续的内存空间中。链表是一种非线性数据结构,它由节点组成,每个节点包含一个数据元素和一个指向下一个节点的指针。

数组的大小固定,插入和删除元素较为复杂,但是随机访问元素速度快。链表的大小可以动态改变,插入和删除元素较为简单,但是访问元素需要遍历链表。

71. Linux 系统中线程的同步方式有互斥量、信号量和条件变量等。假设现在需要设计一个多线程的应用程序,试分析一下以上几种同步方式分别可在什么场合下使用。

  • 互斥量 用于保护共享资源的访问,只允许一个线程访问共享资源。
  • 信号量 用于控制多个线程的并发访问,可以允许一定数量的线程同时访问共享资源。
  • 条件变量 用于线程之间的通信,一个线程可以通过条件变量等待某个条件满足,另一个线程可以通过条件变量唤醒等待线程。

72. 试简述常用的三极管放大电路和技术等特点。

三极管放大电路是一种常用的电子放大器,由三极管、电阻和电容等元件组成。它具有放大电压和功率的功能,可以将弱信号放大为较强的信号。常用的三极管放大电路有共射放大电路、共基放大电路和共集放大电路等。特点包括增益高、频率响应宽、非线性畸变小等。

73. 出现 Segment fault 的根本原因是什么?常出现的场景有哪些?可举例说明。

出现 Segment fault 的根本原因是访问了一个无效的内存地址。常见的场景有访问空指针、访问已经释放的内存、数组越界等。

例如,以下代码会导致 Segment fault:

int* ptr = NULL;
*ptr = 10;

74. 什么是抽象类?

抽象类是一种只能被继承的类,它不能被实例化。抽象类通常用于定义接口和共享代码,它可以包含纯虚函数和非纯虚函数。纯虚函数是在基类中声明但没有实现的虚函数,它必须在派生类中实现。抽象类可以作为其他具体类的基类,通过继承抽象类,派生类可以实现和扩展抽象类的功能。

75. Linux 系统下 .ko 文件是什么文件?.so 文件是什么文件?

  • .ko 文件是 Linux 内核模块文件,用于扩展和添加内核功能。
  • .so 文件是共享库文件,包含可被多个程序共享和调用的函数和数据。

76. 动态库和静态库有什么区别?

动态库和静态库的区别在于链接方式和加载方式。

  • 静态库 在编译时被链接到目标文件中,程序执行时不需要加载库文件。
  • 动态库 在程序执行时动态加载,可以在运行时替换和升级库文件。

静态库的优点是依赖性低,可移植性强,但是占用较多的磁盘空间。动态库的优点是节省磁盘空间,但是依赖性高,需要保证库文件的版本一致性。

77. 简述 Linux 主设备号与次设备号的作用?

Linux 主设备号用于识别设备驱动程序,次设备号用于识别具体的设备实例。主设备号是一个唯一的标识符,由系统分配给不同类型的设备驱动程序。次设备号是由设备驱动程序自己分配的,用于区分同类型的不同设备实例。

78. 内存泄漏怎么产生的?如何避免?在一个功能应用要求频繁使用内存的场景,该如何有效的管理内存?

内存泄漏是指程序在分配内存后没有正确释放导致内存资源无法再次使用。内存泄漏的产生原因包括未释放动态分配的内存、循环引用等。可以通过合理的内存管理和使用垃圾回收机制来避免内存泄漏。在频繁使用内存的场景下,可以使用内存池技术来提高内存的分配和释放效率。

79. 以 U-BOOT 为例,描述嵌入式 ARM-Linux 启动过程。

U-BOOT 是一种开源的嵌入式引导加载程序,用于启动嵌入式 ARM-Linux 系统。启动过程包括硬件初始化、加载 U-BOOT 程序、设置环境变量、加载内核镜像、启动内核等。

80. C++ 中的空类,默认产生那些类成员函数?

空类默认产生默认构造函数、默认拷贝构造函数、默认析构函数和默认赋值运算符函数。默认构造函数用于创建对象,拷贝构造函数用于对象的拷贝,析构函数用于对象的销毁,赋值运算符函数用于对象的赋值。

C/C++ 常见面试题及解答:从进程、内存到嵌入式系统

原文地址: https://www.cveoy.top/t/topic/jy2Q 著作权归作者所有。请勿转载和采集!

免费AI点我,无需注册和登录