Skip to content

磁盘结构与调度

2026 大纲 五(三)1 磁盘,补充说明点名四项:磁盘结构、格式化、分区、磁盘调度方法。

请求的先后顺序,能决定快十倍

本章一路讲的都是"设备"这个抽象。最后两节落到具体的那一个——磁盘, 因为它是整个系统里最重要、也最值得优化的设备:文件系统在它上面、 虚拟内存的对换区在它上面,而它比内存慢五个数量级。

慢在哪儿?一次磁盘访问的时间由三段组成:

T访问=T寻道磁头移到目标柱面+T旋转延迟等目标扇区转到磁头下+T传输真正读写数据

关键在于这三段里只有第一段与"先服务谁"有关。旋转延迟由转速决定、 传输时间由数据量决定,换个服务顺序它们一点都不会变;只有寻道时间—— 磁头从当前柱面跑到目标柱面的距离——完全取决于你按什么顺序处理请求。

所以磁盘调度算法只能优化寻道时间,而它能优化的幅度极大: 同一批请求,按到达顺序服务要跑 640 个磁道,按最近优先只要 236 个。

这一节的六个算法是一条被前一个的毛病推着走的链: 不看位置就横跳(FCFS)⇒ 那就每次挑最近的(SSTF)⇒ 可远处请求会饿死 ⇒ 那就单调扫过去再折返(SCAN)⇒ 可刚扫过的地方要等一个来回、 而且明明最远请求在 183 却要空跑到 199 ⇒ 前一个毛病催生 C-SCAN、 后一个催生 LOOK,两者合并就是 C-LOOK

再往后还有一个 SCAN 系列没堵上的洞(磁臂粘着),由 N-Step-SCAN 与 FSCAN 补。

一、磁盘的物理结构

概念说明
盘面(Surface)一个盘片有一到两个存储面,每面配一个磁头
磁道(Track)单个盘面上的同心圆环,相邻磁道之间留有间隙(Gap)
扇区(Sector)磁道上的一段弧,磁盘的最小读写单位(通常 512 B);一个扇区即一个盘块
柱面(Cylinder)跨盘面:所有盘面上编号相同的磁道构成一个柱面
磁头(Head)每盘面一个,全部固定在同一根磁臂上,同进同退
容量=盘面数×每面磁道数×每道扇区数×扇区大小

该式只适用于等扇区数的理想模型

早期磁盘每条磁道存相同数目的位,内圈周长短、位密度高,外圈的存储能力被浪费。现代磁盘改为把盘面划成若干环带,同一环带内磁道扇区数相同、外层环带磁道扇区更多,并因几何变复杂而向 OS 提供虚拟几何规格。由此推出:"外圈比内圈快"只在现代磁盘上成立(同样转一圈扫过的扇区更多)。

低级格式化真正往盘上写的,是每个扇区的骨架

间隙让磁头能辨识边界(磁头在连续旋转的介质上读信号,没有分隔就分不清一段信号从哪儿开始);标识符字段里的磁道号、磁头号、扇区号,就是磁盘地址被物理地写在盘面上的地方。这套骨架本身要占地方:某型盘每扇区占 600 B 而只有 512 B 存数据,格式化效率 512/60085.3%——标称容量与格式化后可用容量对不上,一部分原因就在这里。

二、磁盘访问时间

分量含义由什么决定典型量级
寻道时间 Tseek磁臂把磁头移到目标柱面机械运动,与跨越的柱面数有关几~十几 ms
旋转延迟 Trotation等目标扇区转到磁头下方转速,平均为半圈2~8 ms
传输时间 Ttransfer数据在磁头下扫过转速与每道扇区数每扇区几十微秒

取半圈是因为目标扇区落在磁道上任意位置的概率相同,等待时间在 [0,一圈] 上均匀分布。

顺序访问与随机访问的量化走查:同样 8 KB 差 15 倍(想看清旋转延迟该算几次时展开)

某磁盘转速 10000 RPM,平均寻道时间 4.5 ms,每磁道 300 个扇区,扇区 512 B。读一个 8 KB 的文件(16 个扇区),A:16 个扇区连续存放在同一磁道上;B:分散在 16 个不同磁道上。

① 三个基础量

转一圈=6000010000=6 msTrotation=62=3 ms,tsector=6300=0.02 ms

RPM 是"转/分",先换算成"一圈多少毫秒"再折半,比直接套 12r 少一次单位换算出错的机会。单扇区传输时间=转一圈时间 ÷ 每道扇区数,因为转一圈恰好扫过整条磁道。

② 情况 A(同一磁道连续):只需寻道一次、只付一次旋转延迟,然后 16 个扇区连着转过磁头。

TA=4.5+3+16×0.02=7.82 ms

找到第一个目标扇区后磁头一直贴着这条磁道,后续扇区依次转过来,不需要再等——旋转延迟只算一次,这一处最容易多算。

③ 情况 B(分散在 16 个磁道):每个扇区都要单独寻道、单独等旋转。

TB=16×(4.5+3+0.02)=120.32 ms

④ 对比TB/TA15.4 倍。数据量完全相同,仅仅因为物理布局不同就差 15 倍——这是顺序访问远快于随机访问的量化来源,也解释了为什么文件的物理结构要尽量让一个文件的块落在同一柱面或相邻柱面上。

三、磁盘调度算法

演进链上每一步都在修前一个的毛病:

FCFS 不看磁头位置,一远一近的请求交替时磁臂横跳 ⇒ SSTF 每次挑最近的,但贪心只看眼前、远处请求可能饥饿SCAN 单调推进到端点再折返,等待时间有了上界;但刚扫过的磁道要等一个来回(最坏 2T),且明明最远请求在 183 却要空跑到 199 ⇒ 前一个毛病催生 C-SCAN(单向服务、到头直接跳回起点),后一个催生 LOOK(只走到最远请求处就折返)⇒ 两者合并即 C-LOOK

以磁头在 53、磁道范围 0~199、请求队列 98, 183, 37, 122, 14, 124, 65, 67、初始方向向磁道号增大为例:

算法本例的访问序列总寻道依赖方向会饥饿折返点公平性
FCFS53→98→183→37→122→14→124→65→67640——公平(严格按到达序)
SSTF53→65→67→37→14→98→122→124→183236——差,远处请求受歧视
SCAN53→65→67→98→122→124→183→199→37→14331磁道端点较好,但刚扫过的方向要等 2T
C-SCAN53→65→67→98→122→124→183→199→0→14→37382磁道端点(到端点跳回起点)最均匀,最大等待 T+Smax
LOOK53→65→67→98→122→124→183→37→14299最远的请求同 SCAN
C-LOOK53→65→67→98→122→124→183→14→37322最远的请求(跳回最近未处理请求)同 C-SCAN
N-Step-SCAN / FSCAN见下方折叠块介于之间各子队列内按 SCAN额外防磁臂粘着

实际系统中通常使用 LOOK / C-LOOK——它们省掉的正是"最远请求到端点"那段纯空程,没有任何代价。

五种算法的磁头轨迹逐步走查与寻道量统计(想核对每一段距离怎么加出来时展开)

FCFS:按请求到达顺序服务。

53981833712214124656745+85+146+85+108+110+59+2=640

SSTF:每次选离当前磁头最近的请求。

53656737149812212418312+2+30+23+84+24+2+59=236

比 FCFS 少 63%。

SCAN:沿一个方向移动、服务沿途所有请求,到达最远端(0 或最大磁道号)后反向。

536567981221241831993714(19953)+(19914)=146+185=331

C-SCAN:只在一个方向上服务,到达最远端后直接跳回起点重新开始,返程不服务。

5365679812212418319901437146+199+37=382

LOOK:磁头只走到最远的那个请求处就折返。

536567981221241833714130+169=299

C-LOOK:到最远请求后直接跳回最近的未处理请求

536567981221241831437130+169+23=322

若题目明确说"返程不计入寻道距离",则 C-SCAN 为 382199=183,C-LOOK 为 322169=153

磁臂粘着:SCAN 没堵上的那个洞

上面六个算法里,SCAN 系列的卖点是"等待时间有上界"。但它保证的其实只是 "新请求最多等一个来回",并没有保证"磁头一定会往前走"

这两句不一样。磁臂粘着(Arm Stickiness)说的就是后者失守的情形: 若有一个或几个进程反复请求同一磁道,磁臂就会一直停在那儿、垄断整个磁盘。 只要当前磁道上永远有新请求进来,扫描就永远推进不了—— 在高密度磁盘上尤其容易出现。

⚠️ 顺带澄清一处:FCFS 不会磁臂粘着。它严格按到达次序服务, 下一个请求在哪就往哪走,反复请求同一磁道的进程也插不到别人前面。 磁臂粘着是"总挑最近的/按位置扫描"这类算法才有的病

堵这个洞的办法只有一个思路:把当前正在服务的这一批请求冻结起来, 新来的一律另存。这样磁头扫完这批就必须往下走。两个变体都是这个思路:

算法做法为什么能防粘着
N-Step-SCAN把请求队列分成若干个长度为 N 的子队列,各子队列之间按 FCFS 依次处理,每个子队列内部按 SCAN 处理。处理某子队列期间新到的请求放入其他队列正在处理的子队列是冻结的,新请求进不来,磁头必然扫完这批就走
FSCANN-Step-SCAN 的简化:只分成两个队列。把当前所有请求放入第一个队列并按 SCAN 处理,扫描期间新到的请求全部放入第二个队列;处理完第一个再换第二个同上,本质是"当前批冻结 + 新请求另存"

两个边界:N 很大时 N-Step-SCAN 接近 SCAN(一批就装下几乎所有请求);N=1退化为 FCFS

四、提高磁盘 I/O 速度的方法

方法说明优化的是哪一项
磁盘高速缓存在内存中缓存磁盘数据,命中就不下盘整次访问
磁盘调度算法SSTF/SCAN/LOOK 等重排请求次序寻道时间
提前读(预读)读当前块时顺便把后续块读入缓冲区后续访问的整次开销
延迟写修改缓冲区后不立即写盘,置标志,被替换时才写写盘次数
优化物理块分布文件的块尽量放同一柱面或相邻柱面 + 交叉编号/错位命名寻道 + 旋转
虚拟盘(RAM 盘)用内存模拟磁盘存临时文件(内容由用户控制,区别于 OS 透明管理的高速缓存)全部
RAID 磁盘阵列多个磁盘并行工作,支持交叉存取传输时间 + 可靠性
交叉编号的排法与交替因子的推导(想知道那个因子是怎么被算出来的时展开)

交叉编号让逻辑相邻的扇区在物理上间隔排列,读完一个扇区后处理数据的这段时间里,下一个目标扇区刚好转到磁头下方:

物理位置:  0   1   2   3   4   5   6   7
逻辑编号:  0   4   1   5   2   6   3   7

设处理一个扇区的数据需要 tp、单扇区转过磁头需要 tsector,处理期间会转过 k=tp/tsector 个扇区,所以逻辑相邻的两个扇区在物理上应间隔 k 个扇区:

交替因子=k+1=tptsector+1

例:tsector=0.02 ms 时,tp=0.015 ms → 交替因子 2(就是上图那种排法);tp=0.05 ms → k=3,交替因子 4

现代磁盘控制器自带缓存、处理几乎不占时间,因此交替因子普遍取 1(即不交叉)——这项技术是为控制器慢于磁盘的年代设计的

错位命名则是把不同盘面的扇区编号错位排列:所有盘面同步旋转,读完盘面 0 的最后一个扇区后切换到盘面 1 也需要时间,错位后跨盘面连续读取时目标扇区刚好到达。

五、磁盘管理:格式化、分区与文件系统的建立

① 低级格式化(物理格式化):把每条磁道划分成扇区,并把每个扇区的骨架写到盘面上。扇区大小在这一步选定(常见 512 B,现代磁盘多用 4 KB),这是个权衡——取小则每扇区约 88 B 的固定开销占比高,取大则读一条小记录也要整扇区搬、加剧内部碎片。做完之后磁盘有了"扇区"这个可寻址单位,但还没有任何逻辑结构

② 分区:把一块物理磁盘划分成若干分区,逻辑上每个分区就是一块独立的逻辑磁盘一个分区上建立一套独立的文件系统(各分区可用不同类型、互不干扰,这也是同一块硬盘能装两个操作系统的原因)。分区表存在磁盘的 0 号扇区主引导记录 MBR,里面有引导程序分区表;分区表记录每个分区的起始扇区号与大小,并且必须有一个分区被标记为"活动的",否则无法从这块硬盘引导系统。

③ 高级格式化(逻辑格式化):在每个分区上建立一个空的文件系统——按在分区里的排列顺序依次写入引导块、超级块、空闲空间管理结构、FCB/inode 区、根目录五样结构,同时在分区表中标记该分区所使用的文件系统类型。

分区表的 4 个表项限制,与高级格式化那五样结构各管什么(想核对每一步的产出时展开)

传统 MBR 的分区表只有 4 个表项,最多描述 4 个分区。若需要更多,就把其中一个表项做成扩展分区——它不直接存文件,而是作为容器,内部再用链式的分区描述结构划分出若干逻辑分区

类型能否直接存文件系统能否作为引导分区数量限制
主分区(可被标记为活动分区)最多 4 个(含扩展分区在内)
扩展分区不能(它只是容器)不能最多 1 个
逻辑分区一般不能受扩展分区大小限制

规则一句话:主分区最多 4 个;要超过 4 个分区,必须牺牲一个主分区名额换成扩展分区,在里面开逻辑分区。

另外,分区不是"把盘切开",而是"给盘划权属":它没有在物理上移动任何数据,只是在 MBR 里写了几行"从哪个扇区到哪个扇区归谁"。删掉分区表数据其实还在盘上——这就是分区表损坏后有可能靠工具"恢复分区"的原理。

高级格式化写进去的五样结构各管什么:

写入的结构作用详见
引导块存放该分区的引导程序(若这是活动分区,MBR 里的引导程序会跳到这里)操作系统的引导
超级块记录全局参数:文件系统类型、块大小、块总数与空闲块数、inode 总数、根目录的 inode 号文件系统的全局结构
空闲空间管理结构位示图 / 空闲链表 / 成组链接法,记录哪些块还没被占用外存空闲空间管理
文件控制块 FCB / inode 区存放文件的元数据,此时全部置为空闲;区的大小在这一步定死并写进超级块文件元数据与索引节点
根目录文件系统的入口,从这里才能一层层找到别的文件目录

超级块非有不可的理由:后面几个区各有多大、从哪个块开始,全靠它记着——空闲管理结构和 inode 区的大小是格式化时按分区容量算出来的,不是固定值。所以超级块一坏,整个分区就读不出来了,文件系统通常要在盘上留多份副本。

高级格式化做完之后,分区成为一个可以创建文件的空文件系统,但它并不是空的:上面这五样结构本身就占掉一部分空间,这是"新盘刚格式化就少了几十 MB"的另一个原因。

裸盘(raw disk):分区之后不建文件系统,直接把整个分区当作一个大的线性扇区数组使用。数据库系统自带缓冲池、页管理、日志与崩溃恢复,交换分区(虚拟内存的对换区)只讲速度、不需要目录与文件名——两者套一层文件系统都只是徒增开销。代价是普通程序完全无法访问它。

六、坏块管理

方法由谁做说明
在文件分配表中标记坏块操作系统(简单方法)如 FAT 表里把坏块标为已占用,从此不再分配。软件层面可见
扇区备用(备用扇区替换)磁盘控制器(硬件自动映射)低级格式化时预留备用扇区,发现坏扇区后由控制器把该逻辑扇区重映射到备用扇区,对 OS 完全透明

第二种更好的原因是逻辑地址不变,上层的文件结构不必调整;代价是备用扇区通常不在原位,重映射后访问该扇区会多一次寻道。

考点速记

  1. 磁盘地址是"柱面号 + 盘面号 + 扇区号",柱面放在最前——因为所有盘面的磁头同进同退,寻道以柱面为单位;同一柱面上的各盘面不用再寻道,换个磁头就行。
  2. 访问时间三段中只有寻道时间与服务次序有关,旋转延迟由转速定、传输时间由数据量定。所以调度算法只能优化寻道时间。
  3. 六个算法由两个维度组合而成带不带 C(到头后是折返还是跳回起点)× SCAN 还是 LOOK(折返点是磁道端点还是最远的请求)。
  4. 只有 SSTF 会饥饿(贪心只看眼前,远处请求可能永远轮不上);SCAN 系列都不会,因为它单调推进、等待时间有上界。
  5. C 系列用更大的总寻道距离换更均匀的等待:C-SCAN 的最大等待是 T+Smax,而 SCAN 下刚扫过的方向要等一个来回(最坏 2T)。
  6. 实际系统通常用 LOOK / C-LOOK——它们省掉的正是"最远请求到端点"那段纯空程,没有任何代价。
  7. ⚠️SCAN 系列保证的是"新请求最多等一个来回",不保证"磁头一定往前走"。 反复请求同一磁道就会磁臂粘着FCFS 不会磁臂粘着——它严格按到达序,插不了队。
  8. N-Step-SCAN / FSCAN 防粘着的思路只有一个:冻结当前批,新请求另存。 N 很大时接近 SCAN,N=1 时退化为 FCFS。
  9. 初始化三步各写各的低级格式化划扇区写骨架、分区在 MBR 写分区表(两者整盘各一次)、高级格式化每分区各建一次空文件系统;不建文件系统即裸盘
  10. 能改善磁盘 I/O 性能的:重排 I/O 请求次序、预读与滞后写、优化文件物理块的分布。⚠️在一个磁盘上设置多个分区不能——分区是逻辑划分,不改变物理特性。

这一节在真题里被考过的形式

磁盘调度是 io 章出题最稳的一节,几乎年年一道手算题,另有两道大题的分问落在这里。 问法只有两类。

  • ① 给磁头位置、移动方向和请求序列,用指定算法算访问顺序或总移过的磁道数(2009-29 SCAN、2015-32 SCAN、2021-26 SSTF、2024-32 C-SCAN)。这类题的做法完全固定,但有三处必须先在题干里确认,任何一处默认错整题就错:

    • 当前磁头位置当前移动方向(SCAN 系列必须给方向,方向不同答案完全不同);
    • 磁道号范围(决定 SCAN 会走到 199 还是 399,也决定 C-SCAN 跳回 0 还是别处);
    • 是 SCAN 还是 LOOK——题面说"扫描算法/电梯算法"通常指 SCAN(走到端点),说"只到最远请求处折返"才是 LOOK。⚠️ 这一处最容易丢分:SCAN 要把"磁头空跑到端点"那一段距离算进去,LOOK 不算。

    算总移过磁道数时,把访问序列排出来后逐段取相邻两数之差的绝对值再求和即可; C-SCAN 从端点跳回起点那一跳通常也要计入(除非题目明确说不计)。

  • ② 概念判断(2018-30、2012-32)。2018-30 问"系统总是访问某个磁道而不响应其他磁道的访问请求"是什么现象,答磁臂粘着;⚠️ 同题还问哪种算法不会出现它——答 FCFS(速记第七条)。2012-32 问哪一项不能改善磁盘 I/O 性能,答在一个磁盘上设置多个分区(与缓冲区管理共享)。

  • ③ 大题分问(2010-45、2019-44)。2010-45 把 C-SCAN 与位示图、旋转延迟串在一起;2019-44 把磁盘容量计算、CHS 地址、SSTF、磁盘驱动串在一起。⚠️ 大题里最容易错的不是调度本身,而是容量与地址的换算——磁盘容量 = 柱面数 × 盘面数 × 每道扇区数 × 扇区大小,而 CHS 地址要按这个层次逐级拆。

复习优先级必须拿满,且手算要练到不看步骤。 第①类是全章唯一的技术动作, 练熟之后是稳定的送分题;做题前先把那三处(位置、方向、SCAN 还是 LOOK)在题干里圈出来。 第七条(磁臂粘着 + FCFS 不会)是概念题的固定考点。大题里的容量换算要单独练一遍。

易错:SCAN 算总寻道距离时漏掉"磁头空跑到端点"那一段。SCAN 走到端点,LOOK 才只走到最远请求

易错:做 SCAN 系列题时不看当前移动方向。方向不同答案完全不同,题干一定会给。

易错:认为 SSTF 不会饥饿。六个算法里只有它会——贪心只看眼前,远处请求可能永远轮不上。

易错:认为 FCFS 也会磁臂粘着。它严格按到达序服务,反复请求同一磁道的进程插不了队。

易错:把磁臂粘着和饥饿当成一回事。饥饿是某个请求等不到,磁臂粘着是磁头整个卡在一处不往前走

易错:认为调度算法也能优化旋转延迟和传输时间。它们与服务次序无关,只有寻道时间能优化。

易错:认为磁盘地址应该把盘面号放最前。柱面号在最前——同一柱面上换盘面不用寻道,换柱面才要。

教材出处
  • 磁盘的数据组织与格式(盘面、磁道、间隙、扇区、环带与虚拟几何):汤小丹《计算机操作系统》6.8.1 节,印刷 p215
  • 温盘磁道的低级格式化布局(30 扇区、每扇区 600 B 含 512 B 数据、标识符字段的 SYNCH 与磁道号/磁头号/扇区号、CRC 字段、各级间隙):同书 6.8.1 节,印刷 p216
  • 分区表存于 0 扇区的主引导记录、必须标记活动分区,以及高级格式化"设置一个引导块、空闲存储管理、根目录和一个空文件系统,同时在分区表中标记该分区所使用的文件系统":同书 6.8.1 节,印刷 p216
  • C-SCAN 把请求延迟由 2T 降为 T+Smax,SCAN 与 CSCAN 的调度示例:同书 6.8.3 节,印刷 p219
  • 磁臂粘着现象与 N 步 SCAN、FSCAN 算法(含 N 很大时接近 SCAN、N=1 时退化为 FCFS):同书 6.8.3 节,印刷 p219

相关知识

设备的基本概念与分类缓冲区管理文件系统的全局结构固态硬盘机械硬盘模拟器使用指南

真题练习