等待状态到就绪态
作者在听课中产生以下疑问:
为什么等待状态的服务完成后会变成就绪状态,而不是立刻返回到运行状态,为什么CPU只会考虑就绪状态的进程?
为了明确地回答这个问题,我们首先需要了解操作系统中的进程状态和调度机制。
进程的状态
- 新建(New):进程正在被创建。
- 运行(Running):进程正在CPU上执行。
- 等待(Waiting/Blocked):进程等待某个事件发生,例如等待I/O操作完成。
- 就绪(Ready):进程已经准备好在CPU上运行,但由于其他原因(如其他进程正在运行)暂时没有被执行。
- 结束(Terminated):进程已完成执行。
让我们考虑上面的问题,当一个进程从等待状态中解除(例如,它等待的I/O操作完成了),它确实是准备好运行的。但是,它不会立即被分配到CPU,而是首先被放入就绪队列,这是由几个原因决定的:
多任务操作系统:现代操作系统通常支持多任务,这意味着它们同时管理多个进程。尽管有多个进程“准备好”运行,但通常只有一个(或在多核系统中是几个)实际在CPU上执行。
公平性:放入就绪队列并等待其轮到运行确保了公平性。例如,如果两个进程几乎同时完成它们的等待状态,直接将其中一个赋予CPU可能会对另一个造成不公平。通过使用就绪队列,操作系统可以根据特定的调度策略(例如,轮转、优先级等)来选择哪个进程先运行。
优化CPU利用率:在等待状态完成后,进程可能仍然需要等待其他资源,例如内存、磁盘、网络带宽等(也就是说,虽然等待状态是运行态受到某一阻塞条件而产生的状态,但是在服务完成之后也有可能需要重新获取除CPU以外的资源)。将这些进程直接放入运行状态可能会导致CPU资源的浪费,因为CPU可能在等待其他资源时处于空闲状态。将进程放入就绪状态并通过调度器进行管理,可以确保CPU始终忙于处理能够有效使用其能力的工作。
响应时间:通过使用就绪队列,操作系统可以确保对交互式应用(如用户界面应用程序)有更快的响应时间。调度策略可能会优先考虑这些交互式进程,因为它们需要快速的用户响应。
预防资源竞争:假设一个进程等待一个特定资源,当这个资源可用时,可能有多个进程都想要使用它。直接运行这些进程可能会导致资源冲突。通过就绪队列和调度策略,操作系统可以更好地管理这些竞争情况。
总之,将进程从等待状态移到就绪状态而不是直接到运行状态,不仅是为了公平性,还涉及到多种资源管理和优化策略,确保系统的整体效率和响应性。
原语与事务
原语(Primitives)和事务(Transactions)确实有很大的区别,并且它们的应用和目的也不同。让我们来详细解析这两个概念:
原语(Primitives)
- 定义:在计算机科学和操作系统中,原语通常是指一个不可中断的操作,这意味着一旦它开始执行,它就会连续地执行到完成,不会被其他进程或操作打断。
- 特点:原语确保了在多任务环境下的操作是原子的,即它们要么完全执行,要么完全不执行,不会处于中间状态。这为并发控制提供了一个基本的手段,例如在实现互斥锁或信号量时。
- 示例:在多线程编程中,对某些共享资源的访问和修改可能需要使用原语来确保数据的一致性和完整性。
事务(Transactions)
- 定义:事务是数据库管理系统(DBMS)中的一个基本概念,代表了一系列操作,这些操作作为一个单一的逻辑单元执行,满足ACID属性(原子性、一致性、隔离性、持久性)。
- 特点:
- 原子性:事务中的所有操作都必须全部完成,如果任何一个操作失败,整个事务都会回滚到开始前的状态。
- 一致性:事务应确保数据库从一个一致的状态转换到另一个一致的状态。
- 隔离性:并发执行的事务彼此隔离,不会相互干扰。
- 持久性:一旦事务完成(提交),其结果就是永久的,即使系统发生故障。
- 示例:在银行转账操作中,从一个账户扣款和向另一个账户存款可以被视为一个事务。
原语确实是一旦开始执行就会执行到底的操作,不会被中断,并且不支持回滚机制。而事务则提供了一个更高级别的抽象,允许一系列操作作为一个单一的逻辑单元来执行,并提供了回滚机制以处理失败的情况。两者在设计和目的上都有其独特性,但都旨在提供系统的正确性和一致性。