Appearance
题目
某系统采用 LRU 页置换算法和局部置换策略,若系统为进程 P 预分配了 4 个页框,进程 P 访问页号的序列为 0, 1, 2, 7, 0, 5, 3, 5, 0, 2, 7, 6,则进程访问上述页的过程中,产生页置换的总次数是( )。
错因
A
把所有"命中"以外的事件都统称"置换"了——发现每次缺页都数一下,但又错过了几次。或者只数到第三次替换就停了,没注意到序列尾部 7 和 6 也都触发了置换。
B
可能是把开头 4 次"装入空页框"的某一次也错算成置换,或者把序列末尾少数一次。LRU 4 页框情况下,置换的标志是"4 个框都已占满 + 又访问了一个不在框里的页"——一一对照才不会数偏。
D
把"缺页次数"当成"置换次数"了。开头 0,1,2,7 各装入一次页框(4 次缺页),但这 4 次没有谁被替换出去——只是把空页框填上,不算置换。把这 4 次也算上就会得到 9 次缺页,再粗略对应到 6 之类的高数。
总解析
关键区分:缺页 ≠ 置换。缺页指访问的页不在内存(要从外存调入);置换指调入时页框已满、必须替换出一个旧页。
LRU 维护"最近最少使用"的栈结构:每次命中把该页拿到栈顶;缺页时调入栈顶;满了就替换掉栈底(最久未访问)。4 个页框满了之后才会发生置换。
逐次走查(栈顶在右):
| 次 | 访问页 | 命中? | 操作 | 栈状态(旧 → 新) | 置换计数 |
|---|---|---|---|---|---|
| 1 | 0 | 缺 | 装入空框 | [0] | 0 |
| 2 | 1 | 缺 | 装入空框 | [0, 1] | 0 |
| 3 | 2 | 缺 | 装入空框 | [0, 1, 2] | 0 |
| 4 | 7 | 缺 | 装入最后一个空框 | [0, 1, 2, 7] | 0 |
| 5 | 0 | 命中 | 提到栈顶 | [1, 2, 7, 0] | 0 |
| 6 | 5 | 缺 | 满了,替换栈底 1 | [2, 7, 0, 5] | 1 |
| 7 | 3 | 缺 | 替换栈底 2 | [7, 0, 5, 3] | 2 |
| 8 | 5 | 命中 | 提到栈顶 | [7, 0, 3, 5] | 2 |
| 9 | 0 | 命中 | 提到栈顶 | [7, 3, 5, 0] | 2 |
| 10 | 2 | 缺 | 替换栈底 7 | [3, 5, 0, 2] | 3 |
| 11 | 7 | 缺 | 替换栈底 3 | [5, 0, 2, 7] | 4 |
| 12 | 6 | 缺 | 替换栈底 5 | [0, 2, 7, 6] | 5 |
置换共 5 次(缺页共 9 次,其中前 4 次只是装入空页框)。
最终答案是 C。