操作系统轮转调度算法代码结果不符问题排查求助
问题分析:你的代码结果是正确的,预期结果存在偏差
首先,先帮你理清这个轮转调度(RR)案例的正确时间线,你会发现你的代码输出的结果才是符合RR调度规则的正确结果,而你之前的预期存在偏差。
正确的RR调度时间线(时间片=3,所有进程0时刻到达)
我们一步步拆解调度过程:
- 0-3:P1运行,剩余突发时间21,时间推进到3
- 3-6:P2运行,剩余突发时间0(完成),完成时间=6 → 周转时间=6-0=6,等待时间=6-3=3
- 6-9:P3运行,剩余突发时间0(完成),完成时间=9 → 周转时间=9-0=9,等待时间=9-3=6
- 9-12:P1运行,剩余突发时间18,时间推进到12
- 12-15:P1运行,剩余突发时间15,时间推进到15
- 15-18:P1运行,剩余突发时间12,时间推进到18
- 18-21:P1运行,剩余突发时间9,时间推进到21
- 21-24:P1运行,剩余突发时间6,时间推进到24
- 24-27:P1运行,剩余突发时间3,时间推进到27
- 27-30:P1运行,剩余突发时间0(完成),完成时间=30 → 周转时间=30-0=30,等待时间=30-24=6
所以最终的正确统计结果就是你代码输出的:
- 等待时间:P1=6、P2=3、P3=6
- 周转时间:P1=30、P2=6、P3=9
- 平均周转时间15.0000,平均等待时间5.0000
你的代码逻辑验证
你的代码核心逻辑是通过两层循环模拟RR调度:外层循环控制调度轮次,内层循环遍历所有进程,处理未完成的进程。
- 每次处理进程时,如果剩余突发时间≤时间片,就直接计算完成时间(
tat[i] = temp + bu[i])并标记进程完成;如果大于时间片,就减去时间片并推进累计时间。 - 这个逻辑准确模拟了RR调度的“循环遍历未完成进程,每次分配时间片”的规则,所以计算结果是正确的。
可选改进点:更贴近真实队列的实现
你的代码目前假设所有进程都在0时刻到达,如果需要支持非0到达时间的场景,或者更贴近真实调度队列的逻辑,可以改用队列结构实现,这样代码可读性和扩展性更好:
#include<stdio.h> typedef struct { int id; int burst; int arrival; int remaining; } Process; int main() { int n, t; float awt = 0, att = 0; printf("Enter the no of processes -- "); scanf("%d", &n); Process proc[n]; int queue[n], front = 0, rear = 0; int current_time = 0, completed = 0; int tat[n], wt[n]; for (int i = 0; i < n; i++) { proc[i].id = i+1; printf("\nEnter Burst Time for process %d -- ", i+1); scanf("%d", &proc[i].burst); proc[i].remaining = proc[i].burst; proc[i].arrival = 0; // 可修改为输入到达时间 queue[rear++] = i; } printf("\nEnter the size of time slice -- "); scanf("%d", &t); while (completed < n) { int idx = queue[front++]; front %= n; if (proc[idx].remaining <= t) { current_time += proc[idx].remaining; tat[idx] = current_time - proc[idx].arrival; wt[idx] = tat[idx] - proc[idx].burst; proc[idx].remaining = 0; completed++; } else { current_time += t; proc[idx].remaining -= t; queue[rear++] = idx; rear %= n; } } printf("\n\tPROCESS\t BURST TIME \t WAITING TIME\tTURNAROUND TIME\n"); for (int i = 0; i < n; i++) { printf("\t%d \t %d \t\t %d \t\t %d \n", proc[i].id, proc[i].burst, wt[i], tat[i]); awt += wt[i]; att += tat[i]; } printf("\nThe Average Turnaround time is -- %f", att/n); printf("\nThe Average Waiting time is -- %f ", awt/n); return 0; }
这个版本用队列模拟了真实的RR调度流程,能更直观地体现“进程完成一次时间片调度后回到队尾”的规则。
内容的提问来源于stack exchange,提问作者niizz




