面试准备-打卡第一天-操作系统篇

380 阅读11分钟

操作系统是怎么组成的?

计算机系统是由硬件系统和软件系统组成,刚组装成的计算机只有硬件系统,称为“裸机”,操作系统是介于硬件和应用软件之间的一组系统程序,它负责管理和控制计算机硬件和软件系统,协调它们的运行。

操作系统的功能包括进程和处理器管理、作业管理、存储管理、设备管理、文件管理,通过这5大功能调度

操作系统的种类繁多,按照用户界面可以分为命令行操作系统、图形操作系统,按照工作方式可以分成单用户操作系统和多用户操作系统,按照功能和特性的话可以分为批处理操作系统、分时操作系统、实时操作系统、网络操作系统和手机操作系统

什么是进程?什么是线程?两者的区别有哪些?

进程:编写的代码只是一个存储在硬盘的静态文件,通过编译后就会生成二进制可执行文件,当我们运行这个可执行文件后,它就会被装载到内存中,接着CPU会执行程序中的每一条指令,那么这个运行中的程序,就被称为进程

线程: 是进程当中的一条执行流程。

区别:

  • 进程是操作系统分配资源的最小单元
  • 线程是操作系统调度的最小单元

同一个进程内多个线程之间可以共享代码段、数据段、打开的文件等资源,但每个线程各自都有一套独立的寄存器和栈,这样可以确保线程的控制流是相对独立的

协程和进程的区别?

  • 线程和进程都是同步机制,而协程是异步机制
  • 线程是抢占式,而协程是非抢占式。需要用户释放使用权切换到其他协程,因此同一时间其实只有一个协程拥有运行权,相当于单线程能力
  • 一个线程可以有多个协程,一个进程也可以有多个协程
  • 协程不被操作系统内核管理,而完全是由程序控制,线程是被分割的CPU资源,协程是组织好的代码流程,线程是协程的资源。但协程不会直接使用线程,协程直接利用的是执行器关联任意线程或线程池
  • 协程能保留上一次调用时的状态

进程与线程的切换流程是怎么样的?

进程切换分两步:

1、切换页表以使用新的地址空间,一旦去切换上下文,处理器中所有已经缓存的内存地址一瞬间都作废了。

2、切换内核栈和硬件上下文。

对于linux来说,线程和进程的最大区别就在于地址空间,对于线程切换,第1步是不需要做的,第2步是进程和线程切换都要做的。

因为每个进程都有自己的虚拟地址空间,而线程是共享所在进程的虚拟地址空间的,因此同一个进程中的线程进行线程切换时不涉及虚拟地址空间的转换。

串行、并行、并发的区别?

串行在时间上不可能发生重叠,前一个任务没搞定,下一个任务只能等着

并行在时间上是重叠地,两个任务在同一时刻互不干扰的同时执行

并发允许两个任务彼此干扰,统一时间点、只有一个任务运行,交替执行

进程有哪些状态?

进程一共有5种状态,分别是创建、就绪、运行(执行)、终止、阻塞

image.png

  • 运行状态就是进程正在CPU上运行。在单处理机环境下,每一时刻最多只有一个进程处于运行状态。
  • 就绪状态就是说进程已处于准备运行的状态,即进程获得了除CPU之外的一切所需资源,一旦得到CPU即可运行。
  • 阻塞状态就是进程正在等待某一事件而暂停运行,比如等待某资源为可用或等待I/O完成。即使CPU空闲,该进程也不能运行。

运行态→阻塞态:往往是由于等待外设,等待主存等资源分配或等待人工干预而引起的。 阻塞态→就绪态:则是等待的条件已满足,只需分配到处理器后就能运行。 运行态→就绪态:不是由于自身原因,而是由外界原因使运行状态的进程让出处理器,这时候就变成就绪态。例如时间片用完,或有更高优先级的进程来抢占处理器等。 就绪态→运行态:系统按某种策略选中就绪队列中的一个进程占用处理器,此时就变成了运行态。

线程有哪些分类?

从线程的运行空间来说,分为用户级线程(user-level thread, ULT)和内核级线程(kernel-level, KLT)

内核级线程:这类线程依赖于内核,又称为内核支持的线程或轻量级进程。无论是在用户程序中的线程还是系统进程中的线程,它们的创建、撤销和切换都由内核实现。比如英特尔i5-8250U是4核8线程,这里的线程就是内核级线程

用户级线程:它仅存在于用户级中,这种线程是不依赖于操作系统核心的。应用进程利用线程库来完成其创建和管理,速度比较快,操作系统内核无法感知用户级线程的存在

进程间通信的方式有哪些?各自的优缺点?

  • 管道:传输数据是单向的,相互通信需要创建两个管道,通信方式效率低,不适合进程间频繁地交换数据
  • 消息队列:消息队列可以解决管道间频繁地交换数据的问题,但依旧存在通信不及时、附件大小有限制的不足,不适合比较大数据的传输,同时,消息队列通信过程中,存在用户态与内核态之间的数据拷贝开销
  • 共享内存:消息队列的读取和写入的过程,都会发生用户态与内核态的之间的消息拷贝,共享内存的方式就可以很好的解决这个问题,共享内存的机制就是拿出一块虚拟地址空间来,映射到相同的物理内存中,这样,这个进程写入的东西,另一个进程马上就能看到,都不需要拷来拷去传来传去,大大提高了进程间通信的速度。
  • 信号量:使用共享内存的通信方式,带来了新的问题,就是如果多个进程同时修改同一个共享内存,很可能就会发生冲突。所以为了防止多进程竞争共享资源,而造成的数据混乱,所以需要保护机制,使共享的资源在任意时刻只能被一个进程访问,信号量就实现了这一保护机制,它不仅实现访问的互斥性,还可以实现进程间的同步
  • 信号:上面所说的进程间通信,都是常规状态下的工作模式,对于异常情况下的工作模式,都需要用信号的方式来通知进程
  • Socket:前面提到的管道、消息队列、共享内存、信号量和信号都是在同一台主机上进行进程间通信,如果想跨网络与不同主机的进程之间通信,就需要Socket

进程间同步的方式?对应的优缺点?

1、临界区:通过对多线程的串行化来访问公共资源或一段代码,速度快,适合控制数据访问。

优点:保证在某一时刻只有一个线程能访问数据的简便办法。

缺点:虽然临界区同步速度很快,但却只能用来同步本进程内的线程,而不可用来同步多个进程中的线程。

2、互斥量:为协调共同对一个共享资源的单独访问而设计的。互斥量跟临界区很相似,比临界区复杂,互斥对象只有一个,只有拥有互斥对象的线程才具有访问资源的权限。

优点:使用互斥不仅仅能够在同一应用程序不同线程中实现资源的安全共享,而且可以在不同应用程序的线程之间实现对资源的安全共享。

缺点:

  • 互斥量是可以命名的,也就是说它可以跨越进程使用,所以创建互斥量需要的资源更多,所以如果只为了在进程内部是用的话使用临界区会带来速度上的优势并能够减少资源占用量。
  • 通过互斥量可以指定资源被独占的方式使用,但如果有下面一种情况通过互斥量就无法处理,比如现在一位用户购买了一份三个并发访问许可的数据库系统,可以根据用户购买的访问许可数量来决定有多少个线程/进程能同时进行数据库操作,这时候如果利用互斥量就没有办法完成这个要求,信号量对象可以说是一种资源计数器。

3、信号量:为控制一个具有有限数量用户资源而设计。它允许多个线程在同一时刻访问同一资源,但是需要限制在同一时刻访问此资源的最大线程数目。互斥量是信号量的一种特殊情况,当信号量的最大资源数=1就是互斥量了。

优点:适用于对Socket(套接字)程序中线程的同步。

缺点:

  • 信号量机制必须有公共内存,不能用于分布式操作系统,这是它最大的弱点;
  • 信号量机制功能强大,但使用时对信号量的操作分散, 而且难以控制,读写和维护都很困难,加重了程序员的编码负担;
  • 核心操作P-V分散在各用户程序的代码中,不易控制和管理,一旦错误,后果严重,且不易发现和纠正。

4、事件: 用来通知线程有一些事件已发生,从而启动后继任务的开始。

优点:事件对象通过通知操作的方式来保持线程的同步,并且可以实现不同进程中的线程同步操作。

线程间通信的方式有哪些?为什么线程也需要通信?

Java线程的通信方式有以下四种

  • volatile
  • 等待和通知机制(wait和notify)
  • join方式
  • threaLocal 线程通信它是为了使线程间更好的协作,线程无论是交替式执行,还是接力式执行,都需要进行通信告知

线程间同步的方式?

  • 互斥量:采用互斥对象机制,只有拥有互斥对象的线程才有访问公共资源的权限
  • 信号量:它允许同一时刻多个线程访问同一资源,但是需要控制同一时刻访问此资源的最大线程数量
  • 事件(信号):通过通知操作的方式来保持多线程同步,还可以方便的实现多线程优先级的比较操作

什么是临界区?如何解决冲突?

每个进程中访问临界资源的那段程序称为临界区,一次仅允许一个进程使用的资源称为临界资源。

解决冲突的办法:

  • 如果有若干进程要求进入空闲的临界区,一次仅允许一个进程进入,如已有进程进入自己的临界区,则其它所有试图进入临界区的进程必须等待;
  • 进入临界区的进程要在有限时间内退出
  • 如果进程不能进入自己的临界区,则应让出CPU,避免进程出现“忙等”现象。