操作系统(Linux)--按优先数调度算法实现处理器调度

这道题慢悠悠地做,出现了很多错误,大多都是空指针产生的中断,最后还是实现了,代码写得有点乱,有时间优化下(当然有同学指点下也是不错的,哈哈)。


实习题目:

设计一个按优先数调度算法实现处理器调度的程序。

[提示]:

(1) 假定系统有5个进程,每个进程用一个PCB来代表。PCB的格式为:

进程名、指针、要求运行时间、优先数、状态。

进程名——P1~P5。

指针——按优先数的大小把5个进程连成队列,用指针指出下一个进程PCB的首地址。

要求运行时间——假设进程需要运行的单位时间数。

优先数——赋予进程的优先数,调度时总是选取优先数大的进程先执行。

状态——假设两种状态,就绪,用R表示,和结束,用E表示。初始状态都为就绪状态。

(2) 每次运行之前,为每个进程任意确定它的“优先数”和“要求运行时间”。

(3) 处理器总是选队首进程运行。采用动态改变优先数的办法,进程每运行1次,优先数减1,要求运行时间减1。

(4) 进程运行一次后,若要求运行时间不等于0,则将它加入队列,否则,将状态改为“结束”,退出队列。

(5) 若就绪队列为空,结束,否则,重复(3)。


思路流程图:









对运行时间的判断:


对优先数的判断:





/*
author:huangpingyi
date:2016 11 24
*/
#include <iostream>
#include <time.h>
#include <stdlib.h>
using namespace std;

static int point = 0;//用于计算进程是否运行完成
struct PCB
{
	int pid;
	int priority;
	int time;
	PCB *next;
};

void tailCreate(PCB *L)
{
	srand((unsigned int)time(0));//以时间为随机数种子,保证每次随机数不一样
	int priority = rand() % 5;//随机优先数
	PCB *s, *r = L;
	for (int i = 0; i<5; i++)
	{
		
		//随机时间为1到50
		int number = rand() % 5;
		while (number == 0)
			//如果是0就一直随机,直到出现不是0的为止
			number = rand() % 5;
		//tail_insert用尾插法初始化
		s = new PCB;
		s->pid = i + 1;
		s->priority = (i + priority) % 5 + 1;
		s->time = number;
		if (s->priority != 5 || r->next == NULL)//如果r->next==NULL表示为队列只有一个头结点,就直接插入
		{
			r->next = s;
			r = s;
		}
		if ((s->priority == 5) && (r->next != NULL))//如果队列不为空,就将它放在头结点后面
		{
			s->next = L->next;
			L->next = s;
		}
	}
	r->next = NULL;
}

void run(PCB *L)//运行
{
	PCB *c = L;
	PCB *p = L;

	for (L; L; L = L->next)
	{
		if (L->next == NULL)
			break;
		//由于存在存在头结点,所以从L->next开始
		L->next->priority = L->next->priority - 1;
		L->next->time = L->next->time - 1;
		if (L->next->time == 0)
			//如果运行时间为0,就将它移除队列中
		{
			cout << "run over" <<"->PID->"<< L->next->pid << endl;
			L->next->time = -1;
			L->next = L->next->next;
			//由于出现了L->next = L->next->next;这步,
			//接着执行for循环的第三个表达式,便跳过了L->next->next这个结点,接着执行L->next->next->next这个结点
			//所以需要判断一下L->next->next这个结点
			if (L->next != NULL&&L->next->time != 0)
			{
				L->next->priority = L->next->priority - 1;
				L->next->time = L->next->time - 1;
			}


				//如果L->next->next->time的值等于0,便会将它移除队列,接着执行L->next=L->next->next这步
				//所以需要while循环来判断
				while (L->next != NULL&&L->next->time == 0)
				{
					cout << "run over" <<"->PID->"<< L->next->pid << endl;
					L->next->time = -1;
					L->next = L->next->next;
					point = point + 1;
					if (L->next != NULL)
					{
						L->next->priority = L->next->priority - 1;
						L->next->time = L->next->time - 1;
					}
				}
			point = point + 1;
		}
		if (L->next != NULL&&L->next->priority == 0)//如果优先数为0就将它变成0放在队首
		{
			//******
			PCB *q = L->next;
			L->next = L->next->next;
			q->priority = 5;
			q->next = c->next;
			c->next = q;
			//由于执行了L->next=L->next->next
			//所以又会执行上面那步同样地操作
			if (L->next != NULL&&L->next->time != 0)
			{
				L->next->priority = L->next->priority - 1;
				L->next->time = L->next->time - 1;
			}
			while (L->next != NULL&&L->next->time == 0)
			{
				cout << "run over" << "->PID->"<<L->next->pid << endl;
				L->next->time = -1;
				L->next = L->next->next;
				point = point + 1;
				if (L->next != NULL)
				{
					L->next->priority = L->next->priority - 1;
					L->next->time = L->next->time - 1;
				}
			}
		}


	}
	L = p;
}

int main()
{
	PCB *L, *m;
	L = new PCB;//初始化头结点
	L->next = NULL;
	tailCreate(L);
	m = L;
	L = L->next;

	cout << "=============" << endl;
	cout << "Init" << endl;
	cout << "==============" << endl;
	for (L; L; L = L->next)
	{
		cout <<"PID :"<< L->pid << endl;
		cout << "Time :"<<L->time << endl;
		cout << "Priority :"<<L->priority << endl;
		cout << "******* " << endl;
		cout << endl;
	}
	cout << "=============" << endl;
	cout << "Init successful!" << endl;
	cout << "==============" << endl;
	cout << endl;
	cout << "run order!" << endl;
	while (point != 5)
	{
		run(m);
	}
	system("pause");
	return 0;

}


windows下:




ubuntu:





这里用了srand((unsigned int)time(0));函数以电脑时间为随机数种子,保证每次随机数不一样

这里设置的运行时间为1到5

猜你喜欢

转载自blog.csdn.net/qq_23948283/article/details/53310808