1. 程式人生 > >排程演算法之最短作業優先演算法

排程演算法之最短作業優先演算法

最短作業優先演算法又叫做短程序優先演算法

寫此博文目的:

1.方便自己複習

2.給正在學習此演算法的人一點參考

單道(一次只能執行一個程序)

分析:

先將程序按照到達時間升序排序,第一個程序到達的時候不等待,直接執行,因為他是第一個到達的程序,在他之前沒有程序在執行,當有程序到達但是有其他程序在執行的時候,到達的程序處於等待狀態,當某個正在執行的程序執行完畢的時候,需要選擇下一個程序,依據是:處於等待狀態的程序,且執行時間最短(當有多個程序處於等待狀態的時候,選擇執行時間最短的程序,這個結束最短作業優先演算法的核心)

程式碼如下:

#include<bits/stdc++.h>
using
namespace std; #define TAKEIN "takein"//對應的程序狀態 #define WAIT "wait" #define RUN "run" #define FINISH "finish" #define PNUMBER 5//程序個數 typedef struct pcb { char processName[20];//程序名稱 int arriveTime;//程序到達時間 int startTime;//程序開始時間 int endTime;//程序結束時間 int runTime;//程序執行時間大小 int turnOverTime;//
週轉時間 int userweightTurnOverTime;//帶權週轉時間 char provessStatus[10];//程序狀態 } pcb; pcb pcbs[PNUMBER];//程序陣列 int currentTime=0;//時間 int processIndex=0;//程序的編號 void createPcbs()//程序初始化函式 { freopen("input.txt","r",stdin);//以只讀操作讀檔案 printf("程序名\t到達時間\t執行時間\n"); for(int index=0; index<PNUMBER; index++)//
遍歷所有程序,給程序賦初值 { scanf("%s",pcbs[index].processName); scanf("%d",&pcbs[index].arriveTime); scanf("%d",&pcbs[index].runTime); pcbs[index].endTime=0; pcbs[index].startTime=0; pcbs[index].turnOverTime=0; pcbs[index].userweightTurnOverTime=0; strcpy( pcbs[index].provessStatus,TAKEIN); printf("%s \t%d \t%d\n", pcbs[index].processName, pcbs[index].arriveTime, pcbs[index].runTime); } printf("\n***********************************************\n"); } void printfPcbsInfo()//列印所有程序的所有資訊 { printf("當前時間為:%d時各程序的資訊.....\n\n",currentTime); printf("程序名\t到達時間\t執行時間\t開始時間\t結束時間\t週轉時間\t帶權週轉時間\t狀態\n"); for(int index=0; index<PNUMBER; index++) { printf("%s\t%8d\t%8d\t%8d\t%8d\t%8d\t%8d\t%4s\n",pcbs[index].processName,pcbs[index].arriveTime,pcbs[index].runTime,pcbs[index].startTime,pcbs[index].endTime,pcbs[index].turnOverTime,pcbs[index].userweightTurnOverTime,pcbs[index].provessStatus); } } void sortPcbs()//按到達時間的升序排序 { int minIndex=0,minValue=0; for(int i=0; i<PNUMBER; i++) { minIndex=i; minValue=pcbs[i].arriveTime; for(int j=i; j<PNUMBER; j++) { if(pcbs[j].arriveTime<minValue) { minValue=pcbs[j].arriveTime;//儲存最小的 minIndex=j; } } pcb temp=pcbs[minIndex];//交換 pcbs[minIndex]=pcbs[i]; pcbs[i]=temp; } } int selNectProcess()//下一個程序的選擇,條件:等待狀態&&執行時間最短 { int result=-1; int minTime=100; for(int index=0; index<PNUMBER; index++) { if(strcmp(pcbs[index].provessStatus,WAIT)==0)//程序處於等待狀態 { if(pcbs[index].runTime<minTime)//且執行時間最短 { minTime=pcbs[index].runTime; result=index; } } } return result;//返回下一個執行的程序的編號 } int isHasProcessArrive()//檢查在某一個時間點有沒有程序到達 { int result=-1; for(int index=0; index<PNUMBER; index++) { if(pcbs[index].arriveTime==currentTime)//某個程序的到達時間等於當前時間 { result=index; strcpy(pcbs[index].provessStatus,WAIT);//改變程序狀態 } } return result; } void runProcess(int pindex) { int runTime=pcbs[pindex].runTime; //程序開始,需要改變程序的相關資訊 pcbs[pindex].startTime=currentTime; pcbs[pindex].endTime=pcbs[pindex].startTime+pcbs[pindex].runTime; strcpy(pcbs[pindex].provessStatus,RUN); printfPcbsInfo();//輸出此時程序的資訊 for(int k=1; k<=runTime; k++) //程序執行中 { currentTime++;//時間轉動 isHasProcessArrive(); if(k==runTime)//程序結束條件 { //改變程序相關資訊 strcpy(pcbs[pindex].provessStatus,FINISH); pcbs[pindex].turnOverTime=pcbs[pindex].endTime-pcbs[pindex].arriveTime; pcbs[pindex].userweightTurnOverTime=pcbs[pindex].turnOverTime*1.0/pcbs[pindex].runTime; } printfPcbsInfo();//列印程序此時資訊 } processIndex++;//準備執行下一個程序 currentTime--;//收回一個時刻,因為下一個程序在此時執行 } void startProcess()//開始程序的排程 { int firstArriveTime=pcbs[0].arriveTime;//第一個到達的程序 int nextIndex=0; printfPcbsInfo(); while(1) { currentTime++;//時間流動 isHasProcessArrive();//檢查這個時候有沒有新到達的程序 if(currentTime<firstArriveTime)//第一個程序都沒有到 { printfPcbsInfo(); } else if(currentTime==firstArriveTime) { runProcess(0);//執行程序 } else //第一個程序執行完畢,選擇下一個程序 { nextIndex=selNectProcess(); if(nextIndex!=-1)//存在下一個將要執行的程序 { runProcess(nextIndex); } if(processIndex==PNUMBER)//所有程序執行完畢 break;//跳出迴圈 } } } int main() { createPcbs();//程序相關資訊的初始化 sortPcbs();//程序按照到達時間升序排序 startProcess();//開始程序的排程 return 0; }

輸入文字如下:

執行結果如下:

如果有不足錯誤的地方,歡迎大家拍磚指正哦!!!

天氣不錯。。。