目录
一、实验内容
按优先数调度算法实现处理器调度。
二、实验目的
在采用多道程序设计的系统中,往往有若干个进程同时处于就绪状态。当就绪进程个数大于处理器数时,就必须依照某种策略来决定哪些进程优先占用处理器。本实验模拟在单处理器情况下的处理器调度,帮助学生加深了解处理器调度的工作。
三、实验原理
设计一个按优先数调度算法实现处理器调度的程序。
(1) 假定系统有五个进程,每一个进程用一个进程控制块PCB来代表,进程控制块的格式为:
进程名 |
指针 |
要求运行时间 |
优先数 |
状态 |
其中,进程名——作为进程的标识,假设五个进程的进程名分别为P1,P2,P3,P4,P5。
指针——按优先数的大小把五个进程连成队列,用指针指出下一个进程的进程控制块的首地址,最后一个进程中的指针为“0”。
要求运行时间——假设进程需要运行的单位时间数。
优先数——赋予进程的优先数,调度时总是选取优先数大的进程先执行。
状态——可假设有两种状态,“就绪”状态和“结束”状态。五个进程的初始状态都为“就绪”,用“R”表示,当一个进程运行结束后,它的状态为“结束”,用“E”表示。
(2) 在每次运行你所设计的处理器调度程序之前,为每个进程任意确定它的“优先数”和“要求运行时间”。
(3) 为了调度方便,把五个进程按给定的优先数从大到小连成队列。用一单元指出队首进程,用指针指出队列的连接情况。例:
队首标志
K2
K1 | P1 | K2 | P2 | K3 | P3 | K4 | P4 | K5 | P5 |
0 | K4 | K5 | K3 | K1 | |||||
2 | 3 | 1 | 2 | 4 | |||||
1 | 5 | 3 | 4 | 2 | |||||
R | R | R | R | R | |||||
PCB1 | PCB2 | PCB3 | PCB4 | PCB5 |
(4) 处理器调度总是选队首进程运行。采用动态改变优先数的办法,进程每运行一次优先数就减“1”。由于本实验是模拟处理器调度,所以,对被选中的进程并不实际的启动运行,而是执行:
优先数-1
要求运行时间-1
来模拟进程的一次运行。
提醒注意的是:在实际的系统中,当一个进程被选中运行时,必须恢复进程的现场,让它占有处理器运行,直到出现等待事件或运行结束。在这里省去了这些工作。
(5) 进程运行一次后,若要求运行时间¹0,则再将它加入队列(按优先数大小插入,且置队首标志);若要求运行时间=0,则把它的状态修改成“结束”(E),且退出队列。
(6) 若“就绪”状态的进程队列不为空,则重复上面(4)和(5)的步骤,直到所有进程都成为“结束”状态。
(7) 在所设计的程序中应有显示或打印语句,能显示或打印每次被选中进程的进程名以及运行一次后进程队列的变化。
(8) 为五个进程任意确定一组“优先数”和“要求运行时间”,启动所设计的处理器调度程序,显示或打印逐次被选中进程的进程名以及进程控制块的动态变化过程。
流程图:
代码实现:
#include<stdio.h>
#include<stdlib.h>
#include<time.h>
#pragma warning(disable:4996)
//定义进程结构体
typedef struct process_def
{
char process_name[20];
int process_time;
int process_priority;
char process_status;
} process ;
//打印当前进程的相关参数
void process_print(process m[], int process_num);
//进程运行前按照进程的优先级将进程排序
void process_sort(process m[],int process_num);
//进程的调度
void process_dispatch(process m[],int process_num);
void main()
{
//输入进程相关参数
printf("请输入将要进行的进程数目:>");
int process_num;
scanf("%d", &process_num);
process* processArray = (process*)malloc(sizeof(process) * process_num);
srand(time(NULL));
for (int i =0; i < process_num; i++)
{
printf("\n********************************\n");
printf("请输入第%d个进程的名字:>",i+1);
scanf("%s", &processArray[i].process_name);
//键盘输入相关参数
/*printf("请输入该进程的运行时间:>");
scanf("%d", &processArray[i].process_time);
printf("请输入该进程的优先级:>");
scanf("%d", &processArray[i].process_priority);*/
//通过随机数为进程赋予参数
processArray[i].process_time = rand() % 10 + 1;
processArray[i].process_priority = rand() % 10 + 1;
processArray[i].process_status = 'R';
}
//进行进程的调度
process_sort(processArray, process_num);
process_dispatch(processArray, process_num);
}
void process_print(process m[],int process_num)
{
printf("\n______________________________________________\n");
for (int i = 0; i < process_num; i++)
{
printf("进程名:%s 进程所需时间:%d 进程优先级:%d 进程状态:%c\n",
m[i].process_name, m[i].process_time, m[i].process_priority, m[i].process_status);
}
}
void process_sort(process m[], int process_num)
{
for (int i = 1; i < process_num; i++)
{
for (int j = 0; j < i ; j++)
{
if (m[i].process_priority > m[j].process_priority)
{
process temp = m[i];
for (int p = i - 1; p >= j; p--)
{
m[p + 1] = m[p];
}
m[j] = temp;
}
}
}
process_print(m, process_num);
}
void process_dispatch(process m[], int process_num)
{
while (process_num!=0)
{
if (m[0].process_priority != 0)
{
printf("\n--进程%s正在运行--\n", m[0].process_name);
m[0].process_priority--;
m[0].process_time--;
printf("\n--进程%s的优先级为%d,所需调度时间为%d", m[0].process_name, m[0].process_priority, m[0].process_time);
if (m[0].process_time == 0)
{
m[0].process_status = 'E';
printf("进程%s已调度完成", m[0].process_name);
for (int i = 0; i < process_num - 1; i++)
{
m[i] = m[i + 1];
}
process_num--;
process_print(m, process_num);
}
else if (m[0].process_priority < m[1].process_priority)
{
for (int i = process_num - 1; i >= 1; i--)
{
if (m[0].process_priority <= m[i].process_priority)
{
process temp = m[0];
for (int j = 0; j <= i; j++)
{
m[j] = m[j + 1];
}
m[i] = temp;
break;
}
}
process_print(m, process_num);
}
else process_print(m, process_num);
}
if (m[0].process_priority == 0)
{
printf("\n--进程%s正在运行--\n", m[0].process_name);
m[0].process_time--;
printf("\n--进程%s的优先级为%d,所需调度时间为%d", m[0].process_name, m[0].process_priority, m[0].process_time);
if (m[0].process_time == 0)
{
m[0].process_status = 'E';
printf("进程%s已调度完成", m[0].process_name);
for (int i = 0; i < process_num - 1; i++)
{
m[i] = m[i + 1];
}
process_num--;
process_print(m, process_num);
}
else
{
process temp = m[0];
for (int i = 0; i < process_num - 1; i++)
{
m[i] = m[i + 1];
}
m[process_num-1] = temp;
process_print(m, process_num);
}
}
}
printf("进程调度结束\n");
}