题目:设计一个按照优先级调度算法实现处理机调度的程序
优先级调度算法实现处理机调度的程序设计提示如下:
(1)假设系统有n个进程,每个进程用一个进程控制块(PCB)来代表。进程控制块的格式如下表所示,且参数意义也相同。进程的优先 数、到达时间和估计运行时间由用户程序任意设定,且优先数越低,优先级越高。调度时,总是选择优先级最高的进程运行。
- 链接指针
- 进程的到达时间
- 进程的优先级
- 估计运行时间
- 进程状态
(2)为了调度方便,设计一个指针指向就绪队列的第一个到达进程。另外再设一个当前运行进程指针,指向当前正运行的进程。
(3)处理机调度时,总是选择已经到达队列的优先级最高的进程运行。为了采用动态优先级调度,进程每运行一次,其优先级就减1。
(4)由于本题目是模拟实验,所以对被选中的进程并不实际启动运行,而只是执行如下操作:
- 优先数加1
- 估计运行时间减1
- 输出当前运行进程的名字
用这三个操作来模拟进程的一次运行。
而就绪队列的每个进程优先数减1
(5)进程运行一次后,应判断该进程的剩余运行时间是否为0,若不为0,且其优先级低于就绪队列的其他进程的优先级,则选择一个高优先级进程抢占CPU运行,若该进程的剩余运行时间为0,则将该进程的状态置为完成状态“C”,并撤出就绪队列。
(6)若就绪队列不为空,则重复上述的步骤(4)和(5)直到所有进程都运行完为止。
(7)在所设计的调度程序中,应包含显示或打印语句,以便显示或打印每次选中进程的名称及运行一次后进程的变化以及就绪队列中各进程排队情况。
代码:
#include<iostream>
#include<iomanip>
using namespace std;
#define maxsize 10;//队列容积
int lock = 0;//系统时间
int m;
typedef struct PCB//进程控制块
{
char name;//进程名
PCB* next;//链接指针
int arrTime;//到达时间
int priority;//优先数
int finTime;//估计运行时间
char state;//进程状态 ——R(就绪态)C(完成态)
};
typedef struct Queue //队列
{
PCB* data;
int front;//指向队头元素
int rear;//指向队尾元素的后一个位置
};
void initQue(Queue& q)//初始化队列
{
int capacity = maxsize;
srand((unsigned)time(NULL));
int num = rand() % 2 + 5;//随机产生5~6个进程
q.front = 0;
q.rear = 0;
q.data = (PCB*)malloc(sizeof(PCB) * capacity);
PCB p;
char c = 'a';
while (num--)
{
p.name = c;
c = c + 1;
p.arrTime = rand() % 8 + 1;//随机产生到达时间
p.priority = rand() % 9 + 1;//随机产生优先数
p.finTime = rand() % 6 + 1;//随机产生估计运行时间
p.state = 'R';
q.data[q.rear] = p;
q.rear = (q.rear + 1) % capacity;
}
}
void showQue(Queue& q)//输出进程队列
{
int i = q.front;
for (; i < q.rear; i++)
{
cout << std::left << setw(15) << q.data[i].name << setw(15) << q.data[i].arrTime << setw(15) << q.data[i].priority << setw(15)
<< q.data[i].finTime << setw(15) << q.data[i].state << endl;
}
}
void sort(Queue& q)//冒泡排序,按进程到达时间从小到大排序进程队列
{
for (int i = q.front; i < q.rear - 1; i++)
for (int j = q.front; j < q.rear - 1 - (i - q.front); j++)
{
if (q.data[j].arrTime > q.data[j + 1].arrTime)
{
PCB p;
p = q.data[j + 1];
q.data[j + 1] = q.data[j];
q.data[j] = p;
}
}
}
int minpriority(Queue& q)//找最小优先数
{
int i = q.front;
int j = q.front;
int n;
for (; i < q.rear ; i++)
{
if (q.data[j].priority <= q.data[i].priority)
{
n = j;
}
else n = j = i;
}
return n;
}
void priorityAdd(Queue& q) //优先级加1(优先数减1)
{
for (int i = q.front ; i < q.rear; i++)
if(i!= m) q.data[i].priority -= 1;
}
void deletepriority(Queue& q)//删除完成的进程
{
for (; m < q.rear ; m++)
{
if (m + 1 != q.rear)
q.data[m] = q.data[m + 1];
else q.rear = m;
}
}
void RR(Queue& q)//优先级调度算法
{
int capacity = maxsize;
Queue B;
B.front = 0;//指向队头元素
B.rear = 0;//指向队尾元素的后一个位置
B.data = (PCB*)malloc(sizeof(PCB) * capacity);
int num = q.rear - q.front;
while (num)//判断所有进程是否都运行完成
{
cout << "时间:" << lock << '\t' << '\t';
int x = 1;
while (x)//判断是否多个进程同时到达
{
if (lock >= q.data[q.front].arrTime && q.front < q.rear)//添加到达进程到就绪队列
{
B.data[B.rear] = q.data[q.front];
B.rear = (B.rear + 1) % capacity;
q.front = (q.front + 1) % capacity;
}
else x = 0;
}
if (B.front == B.rear) cout << "当前无进程运行!" << endl;//就绪队列为空
else //就绪队列不为空,则运行队头进程
{
m = minpriority(B);
cout << "当前运行的进程为:" << B.data[m].name << endl;
B.data[m].finTime -= 1;//进程运行时间减1
B.data[m].priority += 1;//优先级减1,即优先数加1
priorityAdd(B);//就绪队列中的进程优先级加1(优先数减1)
cout << "运行进程结束后队列信息如下:\n" << std::left << setw(15)
<< "进程名" << setw(15) << "到达时间" << setw(15) << "优先数" << setw(15) << "剩余运行时间" << setw(15) << "进程状态" << endl;
if (!B.data[m].finTime)//判断进程剩余运行时间是否为0
{
num -= 1;
B.data[m].state = 'C';
showQue(B);
deletepriority(B);
}//是则设置状态为'C',并退出循环队列
else
{
showQue(B);
}//不是则等待下一轮的运行
}
lock += 1;//系统时间加1
}
}
int main()
{
Queue A;
initQue(A);//数据初始化
cout << "随机生成" << A.rear << "个进程,进程信息如下:" << endl << std::left << setw(15) << "进程名" << setw(15) << "到达时间" << setw(15) << "优先数" << setw(15)
<< "运行时间" << setw(15) << "进程状态" << endl;;
showQue(A);//输出进程队列
sort(A);//按到达时间排序
cout << "按到达时间排序后进程信息如下:" << endl << std::left << setw(15) << "进程名" << setw(15) << "到达时间" << setw(15) << "优先数" << setw(15)
<< "运行时间" << setw(15) << "进程状态" << endl;;
showQue(A);//输出进程队列
cout << " 开始执行优先级调度算法处理机调度" << endl << endl;
RR(A);//开始执行优先级调度算法
cout << "所有进程运行完成,总耗时:" << lock << endl;
}