SJF(Shortest Job First,短作业优先)调度算法是一种基于作业执行时间来进行优先级排序的调度算法。其核心思想是优先执行预计运行时间最短的作业,以期望降低平均等待时间和周转时间。SJF算法可以分为抢占式和非抢占式两种。
非抢占式SJF
非抢占式SJF,也称为最短下次CPU执行算法(shortest-next-CPU-burst),在得知当前任务完成后,会选择预计剩余时间最短的任务来执行。这种算法的优点是平均等待时间最小,但缺点是获取下次CPU执行长度比较困难,通常需要估计。
抢占式SJF
抢占式SJF,也称为最短剩余时间优先算法(shortest-remaining-time-first),是在一个任务执行过程中,如果有一个更短剩余时间的任务到达,就会抢占当前任务,转而执行新到达的更短任务。这种算法的优点同样是平均等待时间最小,但实现起来更为复杂。
SJF算法的计算步骤
初始化 :创建一个进程队列,并将所有进程按照到达时间进行排序。选择作业
如果队列中只有一个作业,则直接执行该作业。
如果队列中有多个作业,则选择到达时间最早的作业。
如果多个作业的到达时间相同,则选择预计运行时间最短的作业。
更新队列:
执行选中的作业,并更新队列中其他作业的等待时间和完成时间。
重复步骤2和3,直到所有作业都执行完毕。
代码示例
```c
include include typedef struct { int id; int arrivalTime; int burstTime; int endTime; int waitingTime; } Process; void sortProcessesByArrival(Process processes[], int n) { for (int i = 0; i < n - 1; i++) { for (int j = 0; j < n - i - 1; j++) { if (processes[j].arrivalTime > processes[j + 1].arrivalTime) { Process temp = processes[j]; processes[j] = processes[j + 1]; processes[j + 1] = temp; } } } } void executeProcess(Process *process) { process->startTime = process->arrivalTime; process->endTime = process->startTime + process->burstTime; process->waitingTime = process->startTime - process->arrivalTime; } void SJF(Process processes[], int n) { sortProcessesByArrival(processes, n); int currentTime = 0; for (int i = 0; i < n; i++) { if (currentTime < processes[i].arrivalTime) { currentTime = processes[i].arrivalTime; } executeProcess(&processes[i]); currentTime = processes[i].endTime; } } int main() { int n; printf("Enter the number of processes: "); scanf("%d", &n); Process processes[n]; printf("Enter the arrival times of the processes: "); for (int i = 0; i < n; i++) { scanf("%d", &processes[i].arrivalTime); } printf("Enter the burst times of the processes: "); for (int i = 0; i < n; i++) { scanf("%d", &processes[i].burstTime); } SJF(processes, n); printf("Average Waiting Time: %f\n", calculateAverageWaitingTime(processes, n)); return 0; } float calculateAverageWaitingTime(Process processes[], int n) { float totalWaitingTime = 0; for (int i = 0; i < n; i++) { totalWaitingTime += processes[i].waitingTime; } return totalWaitingTime / n; } ``` 建议 精确估计作业运行时间: SJF算法依赖于对作业运行时间的准确估计。如果估计不准确,可能导致调度性能下降。 SJF算法对长作业不利,因为长作业可能导致其他短作业长时间等待。可以考虑引入优先级调整机制,以平衡长作业处理长作业: