进程调度算法

一、  实验目的

         用C语言模拟进程调度程序,以加深对进程的概念及进程调度算法的理解。

二、实验内容和要求

         设计一个有 N个进程并发执行的进程调度模拟程序。

1.模拟进程数据的生成

         用户选择输入每个进程的到达时间,所需运行时间,进程的运行时间以时间片为单位。

2. 模拟调度程序的功能

         按照模拟数据的到达时间和所需运行时间,能分别执行以下调度算法:

FCFS

SJF

RR

优先级调度算法

 

显示每种算法下各进程的调度执行顺序。

 

计算各进程的开始执行时间,各作业的完成时间,周转时间和带权周转时间。

 

模拟数据结果分析:对同一组模拟数据,比较各算法的平均周转时间,周转系数。

实验方法、步骤及结果测试

         具体算法:

#include<stdio.h>
#include<stdlib.h>
#define MAX 100
/*定义进程结构体*/
typedef struct pcb {
    char name[30];//进程名称
    int priority ;//进程优先数
    float arriveTime;//进程到达时间
    float serveTime;//进程服务时间
    float finishTime;//进程完成时间
    int cpuTime;//进程占用CPU时间
    float roundTime;//带权
    char state;//进程状态
} PCB;

PCB p[MAX];
Output(PCB p[MAX],int n);
PrioritySort(PCB p[MAX],int n);
Run_hrrf(PCB p[MAX] , int n);
Input_sjf(PCB p[MAX],int count);
Input_hrrf(PCB p[MAX],int n);
Input_fcfs(PCB p[MAX],int count);
Input_rr(PCB p[MAX],int count,int num);
void fcfs();
void HRRF();
void FCFS();
void SJF();
void RR();
void Menu() {
    printf("\n\t-----------------欢迎进入进程调度模拟程序-----------------\n");
    printf("\t    ┏━━━━━━━━━━━━━━━━━━━━━━━━━┓\n");
    printf("\t    ┃可选择算法操作:                                  ┃\n");
    printf("\t    ┣━━━━━━━━━━━━┳━━━━━━━━━━━━┫\n");
    printf("\t    ┃1.响应比高者优先调度算法┃2.时间片轮转调度算法    ┃\n");
    printf("\t    ┣━━━━━━━━━━━━╋━━━━━━━━━━━━┫\n");
    printf("\t    ┃3.短作业优先调度算法    ┃4.先来先服务调度算法    ┃\n");
    printf("\t    ┣━━━━━━━━━━━━┻━━━━━━━━━━━━┫\n");
    printf("\t    ┃                   0.退出系统                     ┃\n");
    printf("\t    ┗━━━━━━━━━━━━━━━━━━━━━━━━━┛\n");
}
main() {
    char choice; //算法编号选择
Menu:
    Menu();//显示菜单
    printf("请选择对应序号:");
    scanf("%d",&choice); //输入算法编号
    system("cls");
    switch(choice) {
    case 1:
        printf("\n            *************进程调度算法(响应比高者优先调度算法)************\n\n");
        HRRF();
        break;
    case 2:
        printf("\n            *************进程调度算法(时间片轮转调度算法)************\n\n");
        RR();
        break;
    case 3:
        printf("\n            *************进程调度算法(短作业优先调度算法)************\n\n");
                 SJF();
                break;
    case 4:
        printf("\n            *************进程调度算法(先来先服务调度算法)************\n\n");
        printf("请输入进程数目:");
        FCFS();
        break;
    case 0:
        break;
    default:
        printf("\n输入有误请重新输入。\n");
        break;
    }
    printf(".............回到主菜单......!\n");
    goto Menu ;
} 


Output(PCB p[MAX],int n) {
    int i;
    printf("进程名称\t优先级数\t服务时间\t当前时间\t进程状态\n");
    for(i=0; i<n; i++) {
        printf(" %s\t",p[i].name);
        printf("\t%d\t",p[i].priority);
        printf("\t%f\t",p[i].serveTime);
        printf("\t%d\t",p[i].cpuTime);
        printf("\t%c\t",p[i].state);
        printf("\n");
    }
}

PrioritySort(PCB p[MAX],int n) {
    int m=0,i=0,j ;
    PCB temp;
    m = n;
    for(i = 1 ; i < n ; i++) {
        m = m - 1 ;
        for(j = 0 ; j < m ; j ++) {
            if(p[j].priority < p[j+1].priority) {
                temp = p[j];
                p[j] = p[j+1];
                p[j+1] = temp ;
            }
        }
    }
}

Run_hrrf(PCB p[MAX] , int n) {
    int i ,j ;
    float m=0;
    for(i = 0 ; i < n ; i ++) {
        m = p[i].serveTime+m;
    }
    for(i = 0 ; i <= n ; i ++) {
        for(j = 0 ; j <= m ; j ++) {
            printf("请按回车键继续运行......!\n");
            PrioritySort(p,n);
            getchar();
            p[i].priority--;
            p[i].cpuTime++;
            p[i].serveTime--;
            p[i].state='R';
            Output(p,n);
            if(p[i].serveTime!=0) {
                p[i].state='R';
            } else {
                p[i].state='F';
                break;
            }
        }
    }
}

Input_hrrf(PCB p[MAX],int n) {
    int i;
    for(i=0; i<n; i++) {
        printf("第%d个进程的名称:",i+1);
        scanf("%s",&p[i].name);
        printf("第%d个进程的优先数:",i+1);
        scanf("%d",&p[i].priority);
        printf("第%d个进程的服务时间:",i+1);
        scanf("%f",&p[i].serveTime);
        p[i].state='W';
        p[i].cpuTime=0;
        printf("\n");
    }
}

void HRRF(){
    int number;
    printf("请输入进程数目:");
    scanf("%d",&number); //输入进程数目
    Input_hrrf(p,number);
    PrioritySort(p,number);
    Output(p,number);
    getchar();
    Run_hrrf(p,number);                
}

Input_fcfs(PCB p[MAX],int count) {
    int i ;
    printf("使用FCFS算法:\n");
    for(i=0;i<count;i++){
        printf("输入第 %d 个进程的名字:\n",i+1);
        scanf("%s",&p[i].name);
        printf("输入第 %d 个进程所需的进程时间:\n",i+1);
        scanf("%f",&p[i].serveTime);
    }
}

void fcfs(PCB p[MAX],int count){
    int i ;
    float t;
    float w;
    float s=0;
    float s1=0;
    float sum=0;
    printf("\n");
    printf("所输入的进程如下:\n");
    printf("name\t    serveTime\t\n");
    for(i=0;i<count;i++){
        printf("%s\t    %f\t\n",p[i].name,p[i].serveTime);
    }
    printf("\n");
    printf("算法结果如下:\n");
    printf("number\t    name\t    serveTime\t\n");
    for(i=0;i<count;i++){
        printf("%s\t    %f\t\n",p[i].name,p[i].serveTime);
        s=s+p[i].serveTime;
        p[i].roundTime=s/p[i].serveTime;
        s1=s1+p[i].roundTime;
        sum=sum+s;
    }
    t=sum/count;
    w=s1/count;
    printf("平均作业周转时间为:%f\n",t);
    printf("平均带权周转时间为:%f\n",w);
}

void FCFS(){
    PCB p[MAX];
    int count;
    scanf("%d",&count);
    Input_fcfs(p,count);
    fcfs(p,count);
}

Input_sjf(PCB p[MAX],int count) {
    int i ;
    printf("使用SJF算法:\n");
    for(i=0;i<count;i++){
        printf("输入第 %d 个进程的名字:\n",i+1);
        scanf("%s",&p[i].name);
        printf("输入第 %d 个进程所需的进程时间:\n",i+1);
        scanf("%f",&p[i].serveTime);
        printf("\n");
    }
}

void sjf(PCB p[MAX],int count){
    int i;
    int j;
    float t;
    float w;
    float s=0;
    float s1=0;
    float sum=0;
    PCB temp;
    printf("\n");
    printf("所输入的进程如下:\n");
    printf("name\t    usetime\t\n");
    for(i=0;i<count;i++){
        printf("%s\t    %f\t\n",p[i].name,p[i].serveTime);
    }
    for(i=0;i<count-1;i++){
        for(j=i+1;j<count;j++){
            if(p[j].serveTime<p[i].serveTime)
            {
                temp=p[j];
                p[j]=p[i];
                p[i]=temp;
            }
        }
    }
    printf("\n");
    printf("算法结果如下:\n");
    printf("number\t    name\t    serveTime\t\n");
    for(i=0;i<count;i++){
        printf("%d\t    %s\t    %f\t\n",i+1,p[i].name,p[i].serveTime);
        
    }
    for(i=0;i<count;i++){
        s=s+p[i].serveTime;
        p[i].roundTime=s/p[i].serveTime;
        s1=s1+p[i].roundTime;
        sum=sum+s;
    }
    t=sum/count;
    w=s1/count;
    printf("平均作业周转时间为:%f\n",t);
    printf("平均带权周转时间为:%f\n",w);
}


void SJF(){
    PCB p[MAX];
    int count;
    printf("请输入进程数:\n");
    scanf("%d",&count);
    Input_sjf(p,count);
    sjf(p,count);
}



Input_rr(PCB p[MAX],int count,int num){
    int i , j ;
    for(i=0; i<count; i++) {
        printf("第%d个进程的名称:",i+1);
        scanf("%s",&p[i].name);
        printf("第%d个进程的服务时间:",i+1);
        scanf("%f",&p[i].serveTime);
        printf("\n");
    }
x:
    for(j = 0 ; j < count ; j ++){
        for(i= 0 ; i < num ; i ++){
            if(p[j].serveTime == 0){
                break;
            }else{
                p[j].serveTime--;
            }
        }
        printf("number         serveTime\n    ");
        printf("%s\t    %f\t    \n",p[j].name,p[j].serveTime);
    }
    printf("\n───────────────────────\n");
    if(p[count-1].serveTime!=0){
        goto x ;
    }
}

void RR(){
    PCB p[MAX];
    int count;
    int num;
    printf("请输入进程数:\n");
    scanf("%d",&count);
    printf("请输入时间片时间:");
    scanf("%d",&num);
    Input_rr(p,count,num);
}

 程序主界面:

 

 

优先级调度算法:

时间片轮转(RR)算法:

最短作业优先算法(SJF):

先来先服务算法(FCFS):

 

 

三、实验总结

 

           理论简单,用语言模拟起来比较困难,会出现种种的问题,大部分都得到了解决。本程序还存在各种各样的BUG,参考者需谨慎使用。。。。