Linux系统内核面试题

简介: Linux系统内核面试题

1.如何查看Linux系统中安装的软件包

dpkg --list

CentOS系统中,可以使用以下命令查看已安装的软件包:

yum list installed

2.如何查看Linux系统的CPU占用率?

top:该命令会打印出系统正在运行的进程和相应的资源占用情况,包括CPU占用率、内存占用率等

3.如何查看Linux系统的磁盘使用情况?

可以使用以下命令查看Linux系统的磁盘使用情况:df

该命令会打印出系统中每个文件系统的使用情况,包括已用空间、剩余空间等。

4.如何查看Linux系统的网络连接情况?

netstat:该命令会打印系统中当前的网络连接状态,包括建立的连接、监听的端口等。

5.如何在Linux系统中安装软件包?

yum install <package_name>

6.如何在Linux系统中检查系统日志?

可以使用以下命令查看Linux系统的系统日志:

tail /var/log/syslog

该命令会打印出系统的系统日志,包括系统重要事件、错误信息等。

7.Linux有哪些系统日志文件?

比较重要的是/var/log/messages日志文件。

8.什么是交换空间?

交换空间是Linux使用的一定空间,用于临时保存一些并发运行的程序。当RAM没有足够的内存来容纳正在执行的所有程序时,就会发生这种情况。

9.什么是LILO?

LILO是Linux的引导加载程序。它主要用于将Linux操作系统加载到主内存中,以便它可以开始运行。

10.什么是inode?

储存文件元信息的区域叫做inode,索引节点的意思。

11.什么是硬链接和软链接?

(1)硬链接由于Linux下的文件是通过索引节点来识别文件,硬链接可以认为是一个指针,指向文件索引节点的指针,系统并不为它重新分配inode。每增加一个一个硬链接,文件的链数就加一。

软链接克服了硬链接的不足,没有任何文件系统的限制,任何用户可以创建指向目录的符号链接。因而现在更为广泛使用,它具有更大的灵活性,可以跨越不同机器、不同网络对文件进行连接。

硬链接不可以跨分区,软链接可以。硬链接指向一个inode节点,而软链接则是创建一个新的inode节点。删除硬链接文件,不会删除源文件,删除软链接文件,会把源文件删除。

12.RAID是什么?

RAID全称为独立磁盘冗余阵列,基本思想就是把多个相对便宜的硬盘组合起来,成为一个硬盘阵列组,使性能达到甚至超过一个价格昂贵、容量巨大的硬盘。

13.系统调用与库函数的区别?

系统调用是程序向系统内核请求服务的方式。可以包括硬件相关的服务,或者创建新进程,调度其他进程等。系统调用是程序和操作系统之间的重要接口。

库函数:把一些常用的函数编写完放到一个文件里,编写应用程序时调用。

14.段页式内存管理有何优点?

段页式内存管理结合了段式内存管理和页式内存管理的优点,提供了灵活性、保护性、共享性和虚拟化支持。

灵活性:将内存划分为段和页的组合,既可以方便地管理不同类型的程序和数据,又可以细致地进行内存分配和利用。

保护性:通过设置段和页的访问权限,可以对内存进行精细的访问控制,保护数据的安全性。

共享性:段页式内存管理支持多个程序共享同一段或同一页面,减少内存重复存储,提高内存利用效率。

15.系统调用read( )/write( ),内核具体做了什么?

  • 用户空间发起read()/write()系统调用,并将参数传递给内核。
  • 内核根据系统调用号找到相应的内核函数进行处理,如sys_read()/sys_write()。
  • 内核根据文件描述符找到对应的文件对象,并执行读取或写入操作。
  • 在读取操作中,内核将数据从文件或设备读取到内核空间,并通过页缓存层进行管理。
  • 在写入操作中,内核将数据从用户空间拷贝到内核空间,并通过文件系统层将数据写入文件或设备。
  • 内核可能会通过缓存管理、块设备管理和驱动程序等层次对数据进行处理和传输。

16.static的作用是什么?

  1. 在函数内部声明的静态变量:使用 static 关键字声明的局部变量,会在第一次执行到它们时进行初始化,并且在程序运行期间保持存在。这意味着即使离开了其作用域,下次再进入时仍然可以访问该变量的值。
  2. 在全局范围内声明的静态变量和函数:使用 static 关键字修饰全局变量或者函数,将它们的可见性限制在定义它们的源文件内部。这样做可以避免与其他文件中同名的全局符号冲突。
  3. 在类中声明的静态成员:使用 static 关键字修饰类成员,使得该成员属于整个类而不是对象实例。静态成员被共享并且只有一份副本,可以通过类名直接访问。

17.全局变量和局部变量在内存中是否有区别?如果有,是什么区别?

  1. 存储位置:全局变量在程序的数据段或静态数据区中分配内存,而局部变量通常在栈上分配内存。
  2. 生命周期:全局变量在程序运行期间一直存在,而局部变量只在其所属函数执行期间存在。
  3. 可见性:全局变量对整个程序可见,可以被不同的函数访问。而局部变量仅在定义它的函数内部可见,其他函数无法直接访问。
  4. 初始化:全局变量如果没有显式初始化,则会被自动初始化为零值(如整型为0)。而局部变量没有默认初始化值,需要手动赋值或者初始化。
  5. 内存开销:由于全局变量具有长生命周期,在程序运行期间一直占用内存空间,可能增加内存开销。而局部变量在函数结束时就会释放所占用的栈空间。

18.堆栈溢出一般是由什么原因导致的?

  1. 递归调用深度过大:如果递归函数的层次过多,每个函数调用都会在栈上分配一定的内存空间,当递归层次太深时,可能会超出栈的容量。
  2. 局部变量和数组占用过多空间:当函数内定义的局部变量或者数组占用的内存空间过多时,超出了栈的容量限制,就会发生堆栈溢出。
  3. 函数调用参数传递错误:如果函数调用时传递的参数错误或者参数数量不匹配,可能导致函数内部使用了错误的参数值而引起堆栈溢出。
  4. 递归调用条件不正确:在递归算法中,没有正确设置终止条件,导致无限循环调用自身而造成堆栈溢出。
  5. 缓冲区溢出:当输入数据长度超过程序预留缓冲区大小时,写入数据就会超出缓冲区范围,覆盖到相邻内存空间,从而引起堆栈溢出。

19.构造函数生成对象,析构函数释放对象资源

构造函数(Constructor)用于创建对象并初始化其成员变量。当使用类的构造函数时,会为对象分配内存,并执行必要的初始化操作。

析构函数(Destructor)用于释放对象占用的资源,包括动态分配的内存、打开的文件、建立的网络连接等。在对象被销毁时,析构函数会被自动调用,进行资源的清理和释放操作。

构造函数和析构函数是一对特殊的成员函数,在类定义中没有返回类型,并且与类名相同。构造函数通常用于完成对象的初始化工作,而析构函数则负责对象的清理工作。

20.虚函数、纯虚函数、虚函数表

虚函数(Virtual Function)是在基类中声明的可以被派生类重写的函数。它通过使用关键字virtual来进行声明,并且通过指针或引用调用时,会根据实际对象类型调用相应的派生类函数。虚函数使得在运行时能够实现动态绑定(Dynamic Binding),即根据对象的实际类型来确定要调用的函数。

纯虚函数(Pure Virtual Function)是一个在基类中声明但没有具体实现的虚函数。它使用= 0来进行声明,并且表示该函数没有默认的实现,必须在派生类中进行重写。包含纯虚函数的类称为抽象类,不能直接实例化,只能作为基类供其他子类继承。

虚函数表(Virtual Function Table),也称为vtable,是一种用于实现多态性的机制。当一个类含有虚函数时,编译器会生成一个隐藏的指向虚函数表的指针(vptr),并将其作为对象内部成员之一。这个虚函数表记录了该类所有虚函数及其对应的地址,在运行时决定调用哪个版本的虚函数。

21.常见的数据结构

  • 数组(Array):由一系列相同类型的元素组成,在内存中连续存储。支持通过索引访问元素,时间复杂度为O(1)。
  • 链表(Linked List):由节点组成,每个节点包含一个值和指向下一个节点的指针。可以实现动态插入和删除,但访问需要遍历链表,时间复杂度为O(n)。
  • 栈(Stack):先进后出(LIFO)的数据结构,只允许在栈顶进行插入和删除操作。常用于函数调用、表达式求值等场景。
  • 队列(Queue):先进先出(FIFO)的数据结构,可以在队尾插入元素,在队头删除元素。常用于任务调度、消息传递等场景。
  • 树(Tree):层次结构的非线性数据结构,由节点和边组成。常见的树包括二叉树、二叉搜索树、堆等。
  • 图(Graph):由节点和边组成,表示多个对象之间的关系。可以是有向图或无向图。

22.深拷贝和浅拷贝的区别

拷贝的内容:

  • 浅拷贝只复制对象的指针或引用,不会创建新的对象副本。因此,原对象和拷贝后的对象会共享同一块内存空间。
  • 深拷贝会创建一个全新的独立对象,并将原对象中的所有数据进行复制。这样,在内存中会存在两个完全独立且相同内容的对象。

对象关系:

  • 浅拷贝保留了原始对象和拷贝对象之间的关联关系。如果原始对象发生改变,可能会影响到拷贝后的对象。
  • 深拷贝破除了原始对象和拷贝对象之间的关联关系。它们在内存中是完全独立、互不干扰的。

内存管理:

  • 浅拷贝并不需要额外分配内存,只需简单地复制指针或引用即可。
  • 深拷贝需要分配额外内存来保存完整数据副本,并确保对应资源释放时不会出现冲突。

23.多线程如何保证线程安全

  1. 互斥锁(Mutex):使用互斥锁来实现对共享资源的互斥访问。只有获得锁的线程才能执行临界区代码,其他线程需要等待。
  2. 读写锁(ReadWrite Lock):适用于读操作远远超过写操作的场景。允许多个线程同时读取共享资源,但在写入时需要独占访问。
  3. 原子操作(Atomic Operations):使用原子操作可以确保某个操作是不可分割、不会被中断的。常见原子操作包括自增、自减、交换等。
  4. 条件变量(Condition Variable):用于实现线程间的等待和通知机制。当一个条件不满足时,线程可以等待条件变量;当满足条件时,通过发送信号或广播唤醒等待中的线程。
  5. 线程安全数据结构:选择已经封装好的线程安全数据结构,如并发队列、并发哈希表等。这些数据结构已经考虑了并发访问下的一致性和同步问题。
  6. 同步控制:使用同步控制机制来限制对共享资源的访问。如使用信号量、屏障等来协调线程的执行顺序。
  7. 避免共享数据:尽可能避免多个线程直接访问共享数据,通过消息传递或其他方式来实现线程间的通信。
  8. 线程安全编程范式:在设计和编写代码时,采用一些线程安全的编程范式,如不可变对象、函数式编程等。

24.struct和class的区别

默认成员访问权限:

  • struct:默认的成员访问权限为公共(public)。
  • class:默认的成员访问权限为私有(private)。

继承方式:

  • struct:默认继承方式为公共继承(public inheritance)。
  • class:默认继承方式为私有继承(private inheritance)。

成员函数:

  • struct:可以包含成员函数和构造函数。
  • class:可以包含成员函数、构造函数、析构函数、拷贝构造函数等。

使用习惯:

  • struct:通常用于描述简单的数据结构,并且对成员的访问不加限制。
  • class:通常用于面向对象编程中,封装复杂的数据和行为,并通过接口提供对外部使用者的操作。

25.typedef和define的使用

typedef用于创建类型别名。它可以让我们为已有的数据类型(如基本数据类型、结构体、指针等)定义一个新的名称。这样做可以增强代码的可读性和可维护性,也能简化代码书写过程。

而#define用于创建预处理器宏。它会在编译之前将所有出现该宏名称的地方都替换成对应的文本内容。这通常用于定义常量或者带参数的宏函数。


相关文章
|
16天前
|
算法 Linux 调度
深入理解Linux内核调度器:从基础到优化####
本文旨在通过剖析Linux操作系统的心脏——内核调度器,为读者揭开其高效管理CPU资源的神秘面纱。不同于传统的摘要概述,本文将直接以一段精简代码片段作为引子,展示一个简化版的任务调度逻辑,随后逐步深入,详细探讨Linux内核调度器的工作原理、关键数据结构、调度算法演变以及性能调优策略,旨在为开发者与系统管理员提供一份实用的技术指南。 ####
57 4
|
17天前
|
Linux
在 Linux 系统中,“cd”命令用于切换当前工作目录
在 Linux 系统中,“cd”命令用于切换当前工作目录。本文详细介绍了“cd”命令的基本用法和常见技巧,包括使用“.”、“..”、“~”、绝对路径和相对路径,以及快速切换到上一次工作目录等。此外,还探讨了高级技巧,如使用通配符、结合其他命令、在脚本中使用,以及实际应用案例,帮助读者提高工作效率。
58 3
|
17天前
|
监控 安全 Linux
在 Linux 系统中,网络管理是重要任务。本文介绍了常用的网络命令及其适用场景
在 Linux 系统中,网络管理是重要任务。本文介绍了常用的网络命令及其适用场景,包括 ping(测试连通性)、traceroute(跟踪路由路径)、netstat(显示网络连接信息)、nmap(网络扫描)、ifconfig 和 ip(网络接口配置)。掌握这些命令有助于高效诊断和解决网络问题,保障网络稳定运行。
49 2
|
6天前
|
缓存 网络协议 Linux
深入探索Linux操作系统的内核优化策略####
本文旨在探讨Linux操作系统内核的优化方法,通过分析当前主流的几种内核优化技术,结合具体案例,阐述如何有效提升系统性能与稳定性。文章首先概述了Linux内核的基本结构,随后详细解析了内核优化的必要性及常用手段,包括编译优化、内核参数调整、内存管理优化等,最后通过实例展示了这些优化技巧在实际场景中的应用效果,为读者提供了一套实用的Linux内核优化指南。 ####
24 1
|
11天前
|
算法 Linux 开发者
Linux内核中的锁机制:保障并发控制的艺术####
本文深入探讨了Linux操作系统内核中实现的多种锁机制,包括自旋锁、互斥锁、读写锁等,旨在揭示这些同步原语如何高效地解决资源竞争问题,保证系统的稳定性和性能。通过分析不同锁机制的工作原理及应用场景,本文为开发者提供了在高并发环境下进行有效并发控制的实用指南。 ####
|
11天前
|
Ubuntu Linux 网络安全
linux系统ubuntu中在命令行中打开图形界面的文件夹
在Ubuntu系统中,通过命令行打开图形界面的文件夹是一个高效且实用的操作。无论是使用Nautilus、Dolphin还是Thunar,都可以根据具体桌面环境选择合适的文件管理器。通过上述命令和方法,可以简化日常工作,提高效率。同时,解决权限问题和图形界面问题也能确保操作的顺利进行。掌握这些技巧,可以使Linux操作更加便捷和灵活。
15 3
|
18天前
|
缓存 负载均衡 Linux
深入理解Linux内核调度器
本文探讨了Linux操作系统核心组件之一——内核调度器的工作原理和设计哲学。不同于常规的技术文章,本摘要旨在提供一种全新的视角来审视Linux内核的调度机制,通过分析其对系统性能的影响以及在多核处理器环境下的表现,揭示调度器如何平衡公平性和效率。文章进一步讨论了完全公平调度器(CFS)的设计细节,包括它如何处理不同优先级的任务、如何进行负载均衡以及它是如何适应现代多核架构的挑战。此外,本文还简要概述了Linux调度器的未来发展方向,包括对实时任务支持的改进和对异构计算环境的适应性。
38 6
|
17天前
|
安全 网络协议 Linux
本文详细介绍了 Linux 系统中 ping 命令的使用方法和技巧,涵盖基本用法、高级用法、实际应用案例及注意事项。
本文详细介绍了 Linux 系统中 ping 命令的使用方法和技巧,涵盖基本用法、高级用法、实际应用案例及注意事项。通过掌握 ping 命令,读者可以轻松测试网络连通性、诊断网络问题并提升网络管理能力。
55 3
|
4月前
|
存储 Java
【IO面试题 四】、介绍一下Java的序列化与反序列化
Java的序列化与反序列化允许对象通过实现Serializable接口转换成字节序列并存储或传输,之后可以通过ObjectInputStream和ObjectOutputStream的方法将这些字节序列恢复成对象。
|
21天前
|
存储 算法 Java
大厂面试高频:什么是自旋锁?Java 实现自旋锁的原理?
本文详解自旋锁的概念、优缺点、使用场景及Java实现。关注【mikechen的互联网架构】,10年+BAT架构经验倾囊相授。
大厂面试高频:什么是自旋锁?Java 实现自旋锁的原理?