《操做系統》實驗之進程調度

實驗內容:

第一部分:做業調度ios

   做業名算法

要求運行時間ide

   優先級ui

  到達時間spa

  連接指針操作系統

JCB設計

   提示:指針

   (1)假設系統有五個做業,每個做業投入內存後,操做系統僅爲其創建一個進程.日誌

      做業名      ----做業標識code

      要求運行時間----即估計的做業運行時間

      優先級      ----爲之建立進程的基本優先級

      到達時間    ----做業提交的時刻,可用相對時間片時間表示

         /*以上三項可隨機產生(+1)或用戶指定*/

      連接指針    ----指向比本做業晚到來或同時到來而運行時間較短的做業

   (2)建立做業後應造成按主關鍵字爲到達時間, 次關鍵字爲要求運行時間的做業後備隊列.

   (3)設置系統計時域,記錄運行過的時間片個數,當它的值與做業後備隊列隊首的一個或多個做業的到達時間一致時,將它(們)投入就緒隊列.

   (4)應有顯示或打印語句,能顯示或打印每通過一個系統時間後,就緒隊列及做業後備隊列的狀態.

 

第二部分:進程調度

   (一)優先級調度:

   進程名

  連接指針

要求運行時間

   優先級

  進程狀態

                      PCB

   提示:

      (1)

優先級     ----做業投入就緒隊列,爲其建立進程時將做業的基本優先級寫入,調度時老是選擇優先級最高的進程運行

進程名      ----爲做業建立進程時起的名稱

連接指針    ----指向就緒隊列的下一個進程,就緒隊列以優先級爲基礎排序

要求運行時間----進程運行的相對時間片時間,由爲之建立進程的做業處獲得

進程狀態    ----爲簡單起見,假定進程僅有就緒和完成狀態.進程建立時處於就緒態’R’,運行結束後,置爲完成狀態’C’,並從就緒隊列中刪除.

    (2)爲調度方便,設置一個指針指向就緒隊列的第一個進程.

    (3)處理機調度時,選擇隊首進程運行……將隊首進程摘除後,運行一個時間片,即執行優先級減1、時間片減一的工做. 若此時要求運行時間爲0:此進程運行完畢,狀態置爲’C’;若不爲0,則比較其優先級與隊首進程的優先級:當大於等於隊首進程的優先級時,繼續執行一個時間片,直至小於隊首進程的優先級爲止,將其插入到就緒隊列的合適位置上,再調度隊首進程投入運行.

   (4)所設計的程序應有顯示或打印語句,顯示或打印選中進程的進程名及運行一次後進程就緒隊列及後備做業隊列的狀態.

(二)時間片輪轉法:(+2)

   進程名

  連接指針

要求運行時間

  進程狀態

   PCB

   提示:

   (1)連接指針----指向下一個到來進程的PCB首地址,最後一個進程指出第一個進程的PCB首地址.

         其它如上題

   (2)設置一個隊首指針指向就緒循環隊列的隊首進程.如有新的進程到來,則將其插入到就緒循環隊列的尾端,等待下次調度.

   (3)執行處理機調度時,老是選擇隊首進程運行.僅執行要求運行時間減一的工做.

   (4)進程運行一次後,判斷運行時間是否爲0:若爲0,則置狀態爲’C’,並推出循環就緒隊列;若不爲0,將其置於循環隊列的尾端,等待下一輪的運行.

   (5)若就緒隊列不空,反覆執行(3)、(4)步驟,直至全部進程都運行完爲止.

   (6)所設計的調度程序中,應包含顯示或打印語句,以便顯示或打印每次選中的進程名及運行一次後進程就緒隊列和做業後備隊列的變化狀況.

實現:

  我並無徹底按照實驗內容來作。

  實現的算法是短進程優先以及時間片輪轉,進程由做業生成。

程序流程以下:

  一、首先隨機生成多個做業,對生成的做業按到達時間排序。

  二、時間片輪轉開始。

  三、檢查就緒隊列、後備隊列、做業調度表是否都爲空。若是是,跳到7,程序結束,不然繼續執行。

  四、檢查是否有做業到達。如有做業到達,將做業投入後備隊列,並按短進程優先排序,同時檢查就緒隊列是否已滿。若是沒有做業到達,則進行下一步。

  五、若是就緒隊列不滿,且後備隊列不爲空,則將後備隊列隊首轉換爲進程投入就緒隊列隊尾;後備隊列爲空,則不作處理。若是就緒隊列已滿,則進行下一步。

  六、提取就緒隊列隊首進程放入運行隊列,將其運行時間-1,而後檢查運行時間是否爲0。若運行時間爲0,將進程投入已完成隊列隊尾;若運行時間不爲0,將進程投入回就緒隊列隊尾。

  七、程序結束。

程序中有5種隊列,做業調度表,後備隊列,就緒隊列,運行隊列,已完成隊列。

  做業調度表:存放生成的做業,按到達時間從小到大排序。

  後備隊列:存放雖然已到達,但尚未參與處理機資源分配的做業。

  就緒隊列:存放已到達,且已參與處理機資源分配的做業。輪轉分配資源。

  運行隊列:存放當前正在運行的隊列。同一時間,該隊列最多有一個進程(單處理機)

  已完成隊列:存放運行時間爲0,即已完成的做業。

實驗結果:

  

  

  

  

  此爲運行結果的一部分,完整版能夠見下(因爲是隨機生成做業,因此完整版和截圖並不相同):

    --- 做業調度表 --- 做業名 到達時間 工做時間 Job6 2        1 Job2 2        8 Job9 3        6 Job7 5        3 Job4 6        2 Job3 6        2 Job1 7        1 Job5 8        2 Job8 9        1 # 開始時間片輪轉 ------------------------------------------------------ 當前系統時間 : 1 # 無做業到達 # 就緒隊列: => 空 # 已完成進程隊列: => 空 # 後備隊列: =>------------------------------------------------------ 當前系統時間 : 2 # 將做業Job6投入到後備隊列 # 將做業Job2投入到後備隊列 # 將做業Job6投入到就緒隊列 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process6 1 W --- 後備隊列 --- 做業名 到達時間 工做時間 Job2 2        8    

    --- 做業調度表 --- 做業名 到達時間 工做時間 Job9 3        6 Job7 5        3 Job4 6        2 Job3 6        2 Job1 7        1 Job5 8        2 Job8 9        1 # 進程Process6已完成,退出就緒隊列 # 就緒隊列: => 空 # 已完成進程隊列: => Process6 # 後備隊列: => Job2 ------------------------------------------------------ 當前系統時間 : 3 # 將做業Job9投入到後備隊列 # 將做業Job9投入到就緒隊列 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process9 6 W --- 後備隊列 --- 做業名 到達時間 工做時間 Job2 2        8    

    --- 做業調度表 --- 做業名 到達時間 工做時間 Job7 5        3 Job4 6        2 Job3 6        2 Job1 7        1 Job5 8        2 Job8 9        1 # 就緒隊列: => Process9 # 已完成進程隊列: => Process6 # 後備隊列: => Job2 ------------------------------------------------------ 當前系統時間 : 4 # 無做業到達 # 將做業Job2投入到就緒隊列 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process9 5 W Process2 8 R --- 後備隊列 --- 做業名 到達時間 工做時間 --- 做業調度表 --- 做業名 到達時間 工做時間 Job7 5        3 Job4 6        2 Job3 6        2 Job1 7        1 Job5 8        2 Job8 9        1 # 就緒隊列: => Process2->Process9 # 已完成進程隊列: => Process6 # 後備隊列: =>------------------------------------------------------ 當前系統時間 : 5 # 將做業Job7投入到後備隊列 # 將做業Job7投入到就緒隊列 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process2 8 W Process9 4 R Process7 3 R --- 後備隊列 --- 做業名 到達時間 工做時間 --- 做業調度表 --- 做業名 到達時間 工做時間 Job4 6        2 Job3 6        2 Job1 7        1 Job5 8        2 Job8 9        1 # 就緒隊列: => Process9->Process7->Process2 # 已完成進程隊列: => Process6 # 後備隊列: =>------------------------------------------------------ 當前系統時間 : 6 # 將做業Job4投入到後備隊列 # 將做業Job3投入到後備隊列 # 將做業Job3投入到就緒隊列 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process9 4 W Process7 3 R Process2 7 R Process3 2 R --- 後備隊列 --- 做業名 到達時間 工做時間 Job4 6        2    

    --- 做業調度表 --- 做業名 到達時間 工做時間 Job1 7        1 Job5 8        2 Job8 9        1 # 就緒隊列: => Process7->Process2->Process3->Process9 # 已完成進程隊列: => Process6 # 後備隊列: => Job4 ------------------------------------------------------ 當前系統時間 : 7 # 將做業Job1投入到後備隊列 # 將做業Job1投入到就緒隊列 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process7 3 W Process2 7 R Process3 2 R Process9 3 R Process1 1 R --- 後備隊列 --- 做業名 到達時間 工做時間 Job4 6        2    

    --- 做業調度表 --- 做業名 到達時間 工做時間 Job5 8        2 Job8 9        1 # 就緒隊列: => Process2->Process3->Process9->Process1->Process7 # 已完成進程隊列: => Process6 # 後備隊列: => Job4 ------------------------------------------------------ 當前系統時間 : 8 # 將做業Job5投入到後備隊列 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process2 7 W Process3 2 R Process9 3 R Process1 1 R Process7 2 R --- 後備隊列 --- 做業名 到達時間 工做時間 Job5 8        2 Job4 6        2    

    --- 做業調度表 --- 做業名 到達時間 工做時間 Job8 9        1 # 就緒隊列: => Process3->Process9->Process1->Process7->Process2 # 已完成進程隊列: => Process6 # 後備隊列: => Job5->Job4 ------------------------------------------------------ 當前系統時間 : 9 # 將做業Job8投入到後備隊列 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process3 2 W Process9 3 R Process1 1 R Process7 2 R Process2 6 R --- 後備隊列 --- 做業名 到達時間 工做時間 Job8 9        1 Job5 8        2 Job4 6        2    

    --- 做業調度表 --- 做業名 到達時間 工做時間 # 就緒隊列: => Process9->Process1->Process7->Process2->Process3 # 已完成進程隊列: => Process6 # 後備隊列: => Job8->Job5->Job4 ------------------------------------------------------ 當前系統時間 : 10 # 無做業到達 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process9 3 W Process1 1 R Process7 2 R Process2 6 R Process3 1 R --- 後備隊列 --- 做業名 到達時間 工做時間 Job8 9        1 Job5 8        2 Job4 6        2    

    --- 做業調度表 --- 做業名 到達時間 工做時間 # 就緒隊列: => Process1->Process7->Process2->Process3->Process9 # 已完成進程隊列: => Process6 # 後備隊列: => Job8->Job5->Job4 ------------------------------------------------------ 當前系統時間 : 11 # 無做業到達 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process1 1 W Process7 2 R Process2 6 R Process3 1 R Process9 2 R --- 後備隊列 --- 做業名 到達時間 工做時間 Job8 9        1 Job5 8        2 Job4 6        2    

    --- 做業調度表 --- 做業名 到達時間 工做時間 # 進程Process1已完成,退出就緒隊列 # 就緒隊列: => Process7->Process2->Process3->Process9 # 已完成進程隊列: => Process6->Process1 # 後備隊列: => Job8->Job5->Job4 ------------------------------------------------------ 當前系統時間 : 12 # 無做業到達 # 將做業Job8投入到就緒隊列 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process7 2 W Process2 6 R Process3 1 R Process9 2 R Process8 1 R --- 後備隊列 --- 做業名 到達時間 工做時間 Job5 8        2 Job4 6        2    

    --- 做業調度表 --- 做業名 到達時間 工做時間 # 就緒隊列: => Process2->Process3->Process9->Process8->Process7 # 已完成進程隊列: => Process6->Process1 # 後備隊列: => Job5->Job4 ------------------------------------------------------ 當前系統時間 : 13 # 無做業到達 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process2 6 W Process3 1 R Process9 2 R Process8 1 R Process7 1 R --- 後備隊列 --- 做業名 到達時間 工做時間 Job5 8        2 Job4 6        2    

    --- 做業調度表 --- 做業名 到達時間 工做時間 # 就緒隊列: => Process3->Process9->Process8->Process7->Process2 # 已完成進程隊列: => Process6->Process1 # 後備隊列: => Job5->Job4 ------------------------------------------------------ 當前系統時間 : 14 # 無做業到達 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process3 1 W Process9 2 R Process8 1 R Process7 1 R Process2 5 R --- 後備隊列 --- 做業名 到達時間 工做時間 Job5 8        2 Job4 6        2    

    --- 做業調度表 --- 做業名 到達時間 工做時間 # 進程Process3已完成,退出就緒隊列 # 就緒隊列: => Process9->Process8->Process7->Process2 # 已完成進程隊列: => Process6->Process1->Process3 # 後備隊列: => Job5->Job4 ------------------------------------------------------ 當前系統時間 : 15 # 無做業到達 # 將做業Job5投入到就緒隊列 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process9 2 W Process8 1 R Process7 1 R Process2 5 R Process5 2 R --- 後備隊列 --- 做業名 到達時間 工做時間 Job4 6        2    

    --- 做業調度表 --- 做業名 到達時間 工做時間 # 就緒隊列: => Process8->Process7->Process2->Process5->Process9 # 已完成進程隊列: => Process6->Process1->Process3 # 後備隊列: => Job4 ------------------------------------------------------ 當前系統時間 : 16 # 無做業到達 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process8 1 W Process7 1 R Process2 5 R Process5 2 R Process9 1 R --- 後備隊列 --- 做業名 到達時間 工做時間 Job4 6        2    

    --- 做業調度表 --- 做業名 到達時間 工做時間 # 進程Process8已完成,退出就緒隊列 # 就緒隊列: => Process7->Process2->Process5->Process9 # 已完成進程隊列: => Process6->Process1->Process3->Process8 # 後備隊列: => Job4 ------------------------------------------------------ 當前系統時間 : 17 # 無做業到達 # 將做業Job4投入到就緒隊列 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process7 1 W Process2 5 R Process5 2 R Process9 1 R Process4 2 R --- 後備隊列 --- 做業名 到達時間 工做時間 --- 做業調度表 --- 做業名 到達時間 工做時間 # 進程Process7已完成,退出就緒隊列 # 就緒隊列: => Process2->Process5->Process9->Process4 # 已完成進程隊列: => Process6->Process1->Process3->Process8->Process7 # 後備隊列: =>------------------------------------------------------ 當前系統時間 : 18 # 無做業到達 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process2 5 W Process5 2 R Process9 1 R Process4 2 R --- 後備隊列 --- 做業名 到達時間 工做時間 --- 做業調度表 --- 做業名 到達時間 工做時間 # 就緒隊列: => Process5->Process9->Process4->Process2 # 已完成進程隊列: => Process6->Process1->Process3->Process8->Process7 # 後備隊列: =>------------------------------------------------------ 當前系統時間 : 19 # 無做業到達 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process5 2 W Process9 1 R Process4 2 R Process2 4 R --- 後備隊列 --- 做業名 到達時間 工做時間 --- 做業調度表 --- 做業名 到達時間 工做時間 # 就緒隊列: => Process9->Process4->Process2->Process5 # 已完成進程隊列: => Process6->Process1->Process3->Process8->Process7 # 後備隊列: =>------------------------------------------------------ 當前系統時間 : 20 # 無做業到達 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process9 1 W Process4 2 R Process2 4 R Process5 1 R --- 後備隊列 --- 做業名 到達時間 工做時間 --- 做業調度表 --- 做業名 到達時間 工做時間 # 進程Process9已完成,退出就緒隊列 # 就緒隊列: => Process4->Process2->Process5 # 已完成進程隊列: => Process6->Process1->Process3->Process8->Process7->Process9 # 後備隊列: =>------------------------------------------------------ 當前系統時間 : 21 # 無做業到達 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process4 2 W Process2 4 R Process5 1 R --- 後備隊列 --- 做業名 到達時間 工做時間 --- 做業調度表 --- 做業名 到達時間 工做時間 # 就緒隊列: => Process2->Process5->Process4 # 已完成進程隊列: => Process6->Process1->Process3->Process8->Process7->Process9 # 後備隊列: =>------------------------------------------------------ 當前系統時間 : 22 # 無做業到達 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process2 4 W Process5 1 R Process4 1 R --- 後備隊列 --- 做業名 到達時間 工做時間 --- 做業調度表 --- 做業名 到達時間 工做時間 # 就緒隊列: => Process5->Process4->Process2 # 已完成進程隊列: => Process6->Process1->Process3->Process8->Process7->Process9 # 後備隊列: =>------------------------------------------------------ 當前系統時間 : 23 # 無做業到達 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process5 1 W Process4 1 R Process2 3 R --- 後備隊列 --- 做業名 到達時間 工做時間 --- 做業調度表 --- 做業名 到達時間 工做時間 # 進程Process5已完成,退出就緒隊列 # 就緒隊列: => Process4->Process2 # 已完成進程隊列: => Process6->Process1->Process3->Process8->Process7->Process9->Process5 # 後備隊列: =>------------------------------------------------------ 當前系統時間 : 24 # 無做業到達 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process4 1 W Process2 3 R --- 後備隊列 --- 做業名 到達時間 工做時間 --- 做業調度表 --- 做業名 到達時間 工做時間 # 進程Process4已完成,退出就緒隊列 # 就緒隊列: => Process2 # 已完成進程隊列: => Process6->Process1->Process3->Process8->Process7->Process9->Process5->Process4 # 後備隊列: =>------------------------------------------------------ 當前系統時間 : 25 # 無做業到達 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process2 3 W --- 後備隊列 --- 做業名 到達時間 工做時間 --- 做業調度表 --- 做業名 到達時間 工做時間 # 就緒隊列: => Process2 # 已完成進程隊列: => Process6->Process1->Process3->Process8->Process7->Process9->Process5->Process4 # 後備隊列: =>------------------------------------------------------ 當前系統時間 : 26 # 無做業到達 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process2 2 W --- 後備隊列 --- 做業名 到達時間 工做時間 --- 做業調度表 --- 做業名 到達時間 工做時間 # 就緒隊列: => Process2 # 已完成進程隊列: => Process6->Process1->Process3->Process8->Process7->Process9->Process5->Process4 # 後備隊列: =>------------------------------------------------------ 當前系統時間 : 27 # 無做業到達 --- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 Process2 1 W --- 後備隊列 --- 做業名 到達時間 工做時間 --- 做業調度表 --- 做業名 到達時間 工做時間 # 進程Process2已完成,退出就緒隊列 # 就緒隊列: => 空 # 已完成進程隊列: => Process6->Process1->Process3->Process8->Process7->Process9->Process5->Process4->Process2 # 後備隊列: =>------------------------------------------------------ 當前系統時間 : 28

--- 運行隊列 & 就緒隊列 & 已完成隊列 --- 進程名 運行時間 進程狀態 --- 後備隊列 --- 做業名 到達時間 工做時間 --- 做業調度表 --- 做業名 到達時間 工做時間 # 就緒隊列: => 空 # 已完成進程隊列: => Process6->Process1->Process3->Process8->Process7->Process9->Process5->Process4->Process2 # 後備隊列: =>------------------------------------------------------
View Code

源代碼:

 1 #include <iostream>
 2 #include <stdio.h>
 3 #include <time.h>
 4 #include <stdlib.h>
 5 #include <string.h>
 6 using namespace std;  7 
 8 #define JOBSUM    9    //進程/做業總數
 9 #define JOBNUM    5    //容許的做業道數
 10 #define PRITOP    3    //最高優先級級數
 11 #define TIMELIMIT 10    //時間限制
 12 
 13 struct Job{    //做業
 14     char jname[40];    //做業名
 15     int start;    //到達時間
 16     int pri;    //優先級
 17     int worktime;    //工做時間
 18     Job *next;    //連接指針
 19 };  20 
 21 struct PCB{  22     PCB* next;  23     char pname[40];    //進程名
 24     int time;    //進程運行時間 
 25     char status;    //運行狀態
 26 };  27 
 28 bool CreateJob(Job* jobtable,char name[])    //建立做業,將做業放入做業調度表
 29 {  30     //隨機生成一個做業
 31     Job *p = new Job;  32     strcpy(p->jname,name);  33     p->start = rand()%(TIMELIMIT-1)+1;  34     p->worktime = rand()%(TIMELIMIT-p->start)+1;  35     p->pri = rand()%PRITOP;  36     p->next = NULL;  37 
 38     //將做業放入做業調度表
 39     Job* now = jobtable;  40     
 41     //將做業放入做業調度表,按到達時間排序
 42     if(now->next==NULL){    //後備隊列仍是空的時候
 43         now->next = p;  44  }  45     else{  46         if(p->start <= now->next->start){    //當新生成的做業工做時間比後備隊列第一個做業工做時間就小
 47             p->next = now->next;  48             now->next = p;  49  }  50         else{  51             Job *q = now->next;  52             while( (p->start > q->start) && (q->next!=NULL) ){    //找到插入的位置
 53                 q = q->next;  54  }  55             if( (p->start > q->start) && q->next==NULL){    //新生成的做業的start比後備隊列中全部做業的start都大,則排在最後
 56                 q->next = p;  57  }  58             else if(p->start <= q->start){    //找到插入的位置,這個位置的start小於或者等於下一個節點的start
 59                 Job *t = now->next;  60                 while(t->next!=q){  61                     t = t->next;  62  }  63                 t->next = p;  64                 p->next = q;  65  }  66  }  67  }  68 
 69     return true;  70 }  71 
 72 bool AddHoubei(Job *jobtable,Job *p,Job *&jhead)    //將做業p放入後備隊列jhead,按短做業優先放置
 73 {  74     //將做業p從做業調度表jobtable中去除
 75     Job* q = jobtable;  76     while(q->next!=p && q->next!=NULL){  77         q = q->next;  78  }  79     if(q->next==p){  80         q->next = p->next;  81         p->next = NULL;  82  }  83 
 84     //將做業p放入後備隊列jhead,按短做業優先放置
 85     if(jhead==NULL){    //後備隊列仍是空的時候
 86         jhead = p;  87  }  88     else{  89         if(p->worktime <= jhead->worktime){    //當新生成的做業工做時間比後備隊列第一個做業工做時間就小
 90             p->next = jhead;  91             jhead = p;  92  }  93         else{  94             Job *q = jhead;  95             while( (p->worktime > q->worktime) && (q->next!=NULL) ){    //找到插入的位置
 96                 q = q->next;  97  }  98             if( (p->worktime > q->worktime) && q->next==NULL){    //新生成的做業的worktime比後備隊列中全部做業的worktime都大,則排在最後
 99                 q->next = p; 100  } 101             else if(p->worktime <= q->worktime){    //找到插入的位置,這個位置的worktime小於或者等於下一個節點的worktime
102                 Job *t = jhead; 103                 while(t->next!=q){ 104                     t = t->next; 105  } 106                 t->next = p; 107                 p->next = q; 108  } 109  } 110  } 111     return true; 112 
113 } 114 
115 bool CreateProcess(PCB* &head,PCB* &tail,Job* &jhead)    //建立新進程
116 { 117     PCB* p = new PCB; 118     char JobID = jhead->jname[3]; 119     strcpy(p->pname,"Process");    //進程名 
120     p->pname[7] = JobID; 121     p->pname[8] = '\0'; 122     p->status = 'R';    //就緒狀態
123     p->time = jhead->worktime;        //進程工做時間
124 
125     if(tail==NULL){ 126         //就緒隊列仍是空的,則第一次賦值
127         head = p; 128         tail = head; 129         tail->next = head; 130  } 131     else{ 132         //就緒隊列不爲空
133         tail->next = p; 134         tail = p; 135         p->next = head; 136  } 137 
138     return true; 139 } 140 
141 bool Work(PCB* now)    //當前進程執行
142 { 143     now->time--; 144 
145     return true; 146 } 147 
148 bool DropPro(PCB* &head,PCB* &tail,PCB* &chead,PCB* &ctail)    //將隊首進程,推出循環就緒隊列
149 { 150     PCB* p = head;        //保存頭節點
151     head = head->next;    //頭結點指向他的下一個節點
152     tail->next = head;    //將就緒隊列尾節點直接指向新的頭節點
153     p->next = NULL;        //將分離出來的原來的頭節點的next設爲空NULL
154 
155     if(ctail==NULL){ 156         //已完成進程隊列仍是空的,則第一次賦值
157         chead = p; 158         ctail = chead; 159  } 160     else{ 161         //已完成進程隊列不爲空,則將當前已完成進程放到隊列尾部
162         ctail->next = p; 163         ctail = ctail->next; 164  } 165 
166     return true; 167 } 168 
169 bool NextPro(PCB* &head,PCB* &tail)    //當前進程已執行了一個時間片,將其置於循環隊列尾端。即將head和tail向前推動一次
170 { 171     head = head->next; 172     tail = tail->next; 173 
174     return true; 175 } 176 
177 
178 void printRQ(PCB* head,int readynum)    //打印當前就緒隊列
179 { 180     PCB* p = head; 181     printf("=> "); 182     if(readynum==0){ 183         //就緒隊列已空
184         printf("空\n"); 185         return ; 186  } 187     while(p->next!=head){ 188         printf("%s->",p->pname); 189         p = p->next; 190  } 191     printf("%s\n",p->pname); 192 } 193 
194 void printCQ(PCB* chead,PCB* ctail)    //打印當前已完成進程隊列
195 { 196     PCB* p = chead; 197     printf("=> "); 198     if(chead==NULL){ 199         //已完成進程隊列隊列已空
200         printf("空\n"); 201         return ; 202  } 203     while(p!=ctail){ 204         printf("%s->",p->pname); 205         p = p->next; 206  } 207     printf("%s\n",p->pname); 208 } 209 
210 void printJQ(Job* jhead)    //打印當先後備隊列
211 { 212     Job* p = jhead; 213     printf("=> "); 214     if(jhead==NULL){ 215         printf("空\n"); 216         return ; 217  } 218     while(p->next!=NULL){ 219         printf("%s->",p->jname); 220         p = p->next; 221  } 222     printf("%s\n",p->jname); 223 } 224 
225 void getJobName(int i,char name[])    //得到當前進程名 
226 { 227     //進程名
228     strcpy(name,"Job"); 229     int len = strlen(name); 230     name[len] = '0'+i; 231     name[len+1] = '\0'; 232 } 233 
234 
235 void printProInfo(PCB* now)    //打印當前進程信息
236 { 237     if(now==NULL){ 238         printf("當前沒有進程\n"); 239         return ; 240  } 241     printf("# 當前進程爲\n"); 242     printf("進程名:%s\n",now->pname); 243     printf("運行時間:%d\n",now->time); 244     printf("進程狀態:%c\n",now->status); 245 } 246 
247 void printAllJobInfo(Job* jhead)    //輸出全部做業信息
248 { 249     Job* p = jhead->next; 250     printf("\t--- 做業調度表 ---\n"); 251     printf("做業名\t"); 252     printf("到達時間\t"); 253     printf("工做時間\n"); 254     while(p!=NULL){ 255         printf("%s\t",p->jname); 256         printf("%d\t\t",p->start); 257         printf("%d\n",p->worktime); 258         p = p->next; 259  } 260 } 261 
262 
263 void printQueueInfo(Job *jobtable,Job *jhead,PCB *head,PCB *rhead,PCB *chead,int tablenum,int houbeinum,int readynum)    //打印全部隊列信息
264 { 265     printf("\n"); 266     printf("--- 運行隊列 & 就緒隊列 & 已完成隊列 ---\n"); 267     printf("進程名\t\t"); 268     printf("運行時間\t"); 269     printf("進程狀態\t"); 270     printf("\n"); 271 
272     PCB *p = NULL; 273     //輸出運行隊列信息
274     if(readynum!=0){ 275         p = rhead; 276         printf("%s\t",p->pname); 277         printf("%d\t\t",p->time); 278         printf("%c\t",'W'); 279         printf("\n"); 280  } 281 
282     //輸出就緒隊列信息
283     if(readynum!=0){ 284         p = head->next; 285         while(p!=head){ 286             printf("%s\t",p->pname); 287             printf("%d\t\t",p->time); 288             printf("%c\t",p->status); 289             printf("\n"); 290             p = p->next; 291  } 292  } 293 
294     //輸出完成隊列
295     if(chead!=NULL){    //完成隊列不爲空
296         p = chead; 297         while(p!=chead){ 298             printf("%s\t",p->pname); 299             printf("%d\t\t",p->time); 300             printf("%c\t",p->status); 301             printf("\n"); 302             p = p->next; 303  } 304  } 305 
306 
307     printf("\n"); 308     printf("\t--- 後備隊列 ---\n"); 309     printf("做業名\t"); 310     printf("到達時間\t"); 311     printf("工做時間\t"); 312     printf("\n"); 313 
314     Job *q; 315     //輸出後備隊列
316     if(houbeinum!=0){ 317         q = jhead; 318         while(q!=NULL){ 319             printf("%s\t",q->jname); 320             printf("%d\t\t",q->start); 321             printf("%d\t",q->worktime); 322             printf("\n"); 323             q = q->next; 324  } 325  } 326 
327     printf("\n"); 328     printf("\t--- 做業調度表 ---\n"); 329     printf("做業名\t"); 330     printf("到達時間\t"); 331     printf("工做時間\t"); 332     printf("\n"); 333 
334     //輸出做業調度表
335     if(tablenum!=0){ 336         q = jobtable->next; 337         while(q!=NULL){ 338             printf("%s\t",q->jname); 339             printf("%d\t\t",q->start); 340             printf("%d\t",q->worktime); 341             printf("\n"); 342             q = q->next; 343  } 344  } 345     printf("\n"); 346 } 347 
348 
349 void printQueueInfo2(PCB *head,PCB *chead,PCB *ctail,Job *jhead,int readynum)    //打印全部隊列信息,第二形態,隊列式
350 { 351     printf("\n"); 352     printf("# 就緒隊列:\n"); 353  printRQ(head,readynum); 354 
355     printf("# 已完成進程隊列:\n"); 356  printCQ(chead,ctail); 357 
358     printf("# 後備隊列:\n"); 359  printJQ(jhead); 360 
361     printf("------------------------------------------------------\n"); 362 } 363 
364 int main() 365 { 366     PCB *head=NULL,*tail=NULL;    //就緒隊列
367     PCB *rhead=NULL;    //運行隊列(運行隊列中節點數始終<=1)
368     PCB *chead=NULL,*ctail=NULL;    //已完成進程隊列
369     Job *jhead=NULL;    //後備隊列
370     Job *jobtable = new Job;    //做業調度表
371     jobtable->next = NULL; 372     int i; 373     int tablenum=0;    //做業調度表中做業數量
374     int houbeinum=0;    //後備隊列的做業數量
375     int readynum=0;    //就緒隊列進程數 376 
377     //將結果輸出到日誌文件 378     //freopen("ProcessScheduingLog.log","w",stdout); 379 
380     //初始化
381     srand((unsigned)time(0));    //設置種子
382 
383     for(i=1;i<=JOBSUM;i++){        //初始化每個進程 
384         char name[40]; 385         getJobName(i,name);    //得到做業名
386 
387         if(!CreateJob(jobtable,name)){    //隨機建立一個新做業,放入做業調度表中,做業調度表中做業是無序的。
388             printf("Error 1!\n");    //出現錯誤,直接退出
389             return 0; 390  } 391         else{    //建立成功
392             tablenum++; 393  } 394  } 395  
396     //輸出全部做業信息
397  printAllJobInfo(jobtable); 398 
399     printf("\n"); 400     printf("# 開始時間片輪轉\n"); 401     printf("\n"); 402     printf("------------------------------------------------------\n"); 403 
404     int curtime = 0;    //系統計時域,運行過的時間片個數 405     //時間片輪轉進程調度
406     while(readynum!=0 || houbeinum!=0 || tablenum!=0){    //直到就緒隊列爲空 且 後備隊列爲空 且 做業調度表爲空,退出循環
407         
408         curtime++;    //計時+1
409         printf("當前系統時間 : %d\n",curtime); 410         printf("\n"); 411 
412         //先檢查做業調度表,有到達做業,放入後備隊列
413         bool isArrive = false; 414         Job* p = jobtable->next; 415         while(p!=NULL){ 416             if(p->start==curtime){    //有做業到達,將做業放入後備隊列,並按短做業優先放置
417                 isArrive = true; 418                 Job *t = p->next; 419                 printf("# 將做業%s投入到後備隊列\n",p->jname); 420  AddHoubei(jobtable,p,jhead); 421                 houbeinum++;    //後背隊列
422                 tablenum--;    //做業調度表
423                 p = t; 424  } 425             else{ 426                 p = p->next; 427  } 428  } 429         if(!isArrive){ 430             printf("# 無做業到達\n"); 431  } 432 
433         //檢查就緒隊列是否已滿。不滿,則將後備隊列隊首放入就緒隊列。
434         if(readynum==JOBNUM){    //已滿
435  } 436         else{    //未滿,從後備隊列中將做業放入就緒隊列
437             if(houbeinum!=0){    //後備隊列不爲空
438                 CreateProcess(head,tail,jhead);    //將做業投入到就緒隊列
439                 printf("# 將做業%s投入到就緒隊列\n",jhead->jname); 440                 jhead = jhead->next;    //指向後備隊列下一個做業
441                 readynum++;    //就緒隊列
442                 houbeinum--;    //後備隊列
443  } 444             //已空就算了
445  } 446 
447         PCB* now = head; 448         if(now!=NULL){    //當前就緒隊列不爲空時運行進程 449             //將該進程放入運行隊列
450             rhead = now; 451             //printf("將當前進程放入運行隊列\n");
452 
453             printQueueInfo(jobtable,jhead,head,rhead,chead,tablenum,houbeinum,readynum);    //打印全部隊列信息
454 
455             Work(now);    //執行當前進程
456 
457             if(now->time==0){ 458                 now->status = 'C';    //設置進程爲已完成狀態
459                 printf("# 進程%s已完成,退出就緒隊列\n",now->pname); 460                 DropPro(head,tail,chead,ctail);    //推出循環就緒隊列
461                 readynum--; 462                 if(readynum==0){ 463                     head = 0; 464                     tail = 0; 465  } 466  } 467             else{ 468                 NextPro(head,tail);    //已完成,將其置於循環隊列尾端。即將head和tail向前推動一次
469  } 470 
471  } 472         
473  printQueueInfo2(head,chead,ctail,jhead,readynum); 474 
475  getchar(); 476     
477  } 478     
479     curtime++;    //計時+1
480     printf("當前系統時間 : %d\n",curtime); 481 
482     printQueueInfo(jobtable,jhead,head,rhead,chead,tablenum,houbeinum,readynum);    //打印全部隊列信息
483 
484  printQueueInfo2(head,chead,ctail,jhead,readynum); 485 
486     return 0; 487 }

 

Freecode : www.cnblogs.com/yym2013

相關文章
相關標籤/搜索