为了进一步解释,假设我们有一个没有超线程的双核 CPU,这意味着它只能同时处理 2 个线程,那么,现在假设我们有一个网络应用程序正在运行两个后台网络线程,每个线程都在等待传入连接进行处理,因此这些线程应该一直运行,现在,为什么另一个操作系统的进程和线程仍在运行?!在我看来,它们无法被处理,因为有两个线程完全耗尽了 CPU 处理单元,因为它们正在等待网络传入连接,因此,它们应该每纳秒就准备好连接...这是如何发生和工作的?CPU 如何同时处理许多线程而不会出现任何明显的冻结?!(我知道,有时,如果同时运行许多繁重的程序,Windows 会变得缓慢和疯狂,但这不是一般问题)
谢谢。
答案1
答案相对简单:当一个线程正在等待 I/O 事件时,它会将剩余的时间片交给操作系统,然后操作系统可以调度另一个线程。当高延迟 I/O 完成后,该线程将被标记为准备执行。
这在很大程度上是可能的,因为大多数 I/O 是通过中断来管理的,而不是重复检查 I/O 请求是否已完成(称为轮询)。
答案2
如果您使用协作式多任务处理并且程序很糟糕:那么是的,您是对的。
然而在现实世界中,应该会发生以下情况:
协作式多任务处理:线程不会一直使用 CPU。相反,它会在一段时间后或被阻止时给另一个程序一个机会。Paul
的回答描述了后者。抢占式多任务处理(几乎无处不在):操作系统(而非程序)会在短时间内将 CPU 交给程序,然后将其收回。这可以像运行计时器一样简单,一旦计时器到期,就停止进程并将其交给正在等待的下一个线程/程序。
在你的情况下,可以将其想象成一个有两名员工和三项(或更多)任务的办公室。(我们称之为任务 A、任务 B 和任务 C)。
第一份工作检查主管的命令规定:
- 设置一个 10 分钟的计时器。当它响起时,停止当前任务,将其放在 TODO 列表的底部并继续阅读本文档。
- 接下来从 TODO 列表顶部删除第一项并开始处理它。
- 重复。
工作者 1 设置计时器并获取 TODO 列表的第一个任务(在本例中为任务 A)。
工人 2 做同样的事情:它设置一个计时器并从 TODO 列表顶部获取当前任务。由于工人 1 从中删除了任务 A,工人 2 现在开始执行任务 B。
十分钟后,计时器响起。工人 1 停止处理任务 A,并收到主管的指示。这些指示表明将当前任务放在 TODO 列表的底部。根据主管的指示,它现在重新启动计时器并开始处理现在位于 TODO 列表顶部的任务(即任务 C)。
工作者 2 执行相同操作,停止任务 B,并从 TODO 列表的顶部开始(在示例中为任务 A)
等等等等。
这有点简单。但它应该能让你了解两个踏板(工人)如何 100% 地完成三个或更多的任务。
在实际的调度程序中,还有更多的东西。例如中断(将其与任务中间响起的电话进行比较,并了解如何处理它)、智能调度(将相同的任务交给同一个工作人员可能会导致它更快地完成,因为工作人员已经熟悉它)、I/O(如果工作人员需要从图书馆借书,他不会等到计时器到期,而是立即继续下一个任务,等等。
答案3
操作系统的稳定性与在不同 CPU 上运行多个线程时保持稳定性的方式基本相同。从 CPU 内核外部来看,同一内核中的两个 LP 和两个不同内核中各一个 LP 的行为几乎没有明显差异。在这两种情况下都必须使用相同的“多处理器安全”编程技术,例如信号量。