稍稍有点操作系统基础的朋友应该知道进程的调度算法,在这里Koala还是给大家略微介绍一下接下来将要用到的几种算法:
整个编程思路按照如下进行:
创建主线程,主线程创建子线程,子线程有一个虚拟PCB
主线程创建20个子线程,分别实现FCFS调度、SJF调度、RR调度、优先级调度,并且计算每个调度的平均等待时间。
对于每个子线程,在其运行期间,输出其占用的时间标号(例如,第3个线程占用了第10秒的CPU时间,输出为:“Thread3:10”)。
下面是整个的代码(仅供参考):
#include
#include
#include
#include
#include
#include
#include
#define Thread_Num 20
using namespace std;
pthread_mutex_t Device_mutex ;
//Virtual PCB of threads
struct VirtualPCB
{
int tid;
int priority;
int waittime;
int runtime;
int arrivetime;
int visited;
int tempruntime;
public:
int gettid()
{
return tid;
}
int getwaittime()
{
return waittime;
}
int getpriority()
{
return priority;
}
int getruntime()
{
return runtime;
}
int getarrivetime()
{
return arrivetime;
}
void setvisit(int a)
{
visited=a;
}
int getvisit()
{
return visited;
}
int gettempruntime()
{
return tempruntime;
}
void setwaittime(int n)
{
waittime = n;
}
void settempruntime(int n)
{
tempruntime = tempruntime - n;
}
}TCB[Thread_Num];
//Function to initial virtual PCB
void t_init()
{
int n;
srand(time(NULL));
for(n =0;n1;//用线程创建序号作为虚拟进程id
//用随机数随机产生虚拟PCB的值
TCB[n].priority = 1 + rand()%19;
TCB[n].runtime = 1 + rand()%19;
TCB[n].arrivetime = 0;//模拟时,默认进程按创建顺序依次在0时刻到达
TCB[n].waittime = 0;
TCB[n].visited =0;
TCB[n].tempruntime = TCB[n].runtime;
}
}
//Threads run function
void *t_print(void *arg)
{
int n = *(int *)arg;//get argument
while(1)
{
pthread_mutex_lock(&Device_mutex);
printf("Thread_%-2d: ",n);
printf("tid:%-2d priority:%-2d runtime:%-2d \n",TCB[n-1].gettid(),TCB[n-1].priority,TCB[n-1].runtime);
pthread_mutex_unlock(&Device_mutex);
sleep(1);
break;
}
//printf("Error %d\n",n);
pthread_exit(0);
}
//First come first service schedule function
void FCFS()
{
cout<<"-----------FCFS:"<int i,j;
int start = 0;
float waittime = 0;
float avwait = 0;
for(i=0;i2;i++)
{
for(j=0;jif(TCB[j].getarrivetime()==i && TCB[j].getvisit()==0){
printf("Thread: %-2d Start: %-3d Runtime: %-2d\n",TCB[j].gettid(),start,TCB[j].getruntime());
waittime = waittime + (float)start;
start = start + TCB[j].getruntime();
TCB[j].setvisit(1);
}
}
}
avwait = waittime / (float)Thread_Num;
printf("Total waitting time : %f\n",waittime);
printf("Average waitting time : %f\n",avwait);
}
//Shortest job first schedule function
void SJF()
{
for(int k=0 ;k0);
}
cout<<"-------------SJF:"<int i,j;
int start = 0;
float waittime = 0;
float avwait = 0;
for(i=1;ifor(j=0;jif(TCB[j].getruntime()==i && TCB[j].getvisit()==0){
printf("Thread: %-2d Start: %-3d Runtime: %-2d\n",TCB[j].gettid(),start,TCB[j].getruntime());
waittime = waittime + (float)start;
start = start + TCB[j].getruntime();
TCB[j].setvisit(1);
}
}
}
avwait = waittime / (float)Thread_Num;
printf("Total waitting time : %f\n",waittime);
printf("Average waitting time : %f\n",avwait);
}
//Round R schedule function
void RR(int r)
{
cout<<"--------------RR:"<int start = 0;
float waittime = 0;
float avwait = 0;
for(int i=0;iint totaltime = totaltime + TCB[i].getruntime();
TCB[i].setvisit(0);
}
for(int j=0;j<20*Thread_Num;j=j+r)
{
int k = (j%(20*r))/r;
if(TCB[k].gettempruntime() > 0){
int tepruntime = r;
if(TCB[k].gettempruntime()-r<=0){
tepruntime = TCB[k].gettempruntime();
TCB[k].setwaittime(start + tepruntime - TCB[k].getruntime());
}
printf("Thread: %-2d Start: %-3d Runtime:%-2d \n",TCB[k].gettid(), start,tepruntime);
start = start + tepruntime;
TCB[k].settempruntime(r) ;
}
}
for(int m=0;m//printf("TCB[%d].getwaittime():%d\n",m+1,TCB[m].getwaittime());
}
avwait = waittime / (float)Thread_Num;
printf("Total waitting time : %f\n",waittime);
printf("Average waitting time : %f\n",avwait);
}
//Priority schedule function
void Priority()
{
for(int k=0 ;k0);
}
cout<<"-----------Priority:"<int i,j;
int start = 0;
float waittime = 0;
float avwait = 0;
for(i=1;ifor(j=0;jif(TCB[j].getpriority()==i && TCB[j].getvisit()==0){
printf("Thread: %-2d Start: %-3d Runtime: %-2d\n",TCB[j].gettid(),start,TCB[j].getruntime());
waittime = waittime + (float)start;
start = start + TCB[j].getruntime();
TCB[j].setvisit(1);
}
}
}
avwait = waittime / (float)Thread_Num;
printf("Total waitting time : %f\n",waittime);
printf("Average waitting time : %f\n",avwait);
}
//Main thread execute function to create 20 children threads
void *Children(void*)
{
int ret[Thread_Num];
t_init();
pthread_t tid[Thread_Num];
pthread_mutex_init(&Device_mutex,NULL);
int i,j;
for(i=0;iint k =i+1;
ret[i] = pthread_create(&tid[i],NULL,&t_print, &k);
if(ret[i] == 0) {
sleep(1);
}
else{
printf("Thread_%-2d failed!\n",i+1);
}
}
for(j=0;j0);
}
int main()
{
int ret1;
pthread_t tid1;//Declare main thread
ret1 = pthread_create(&tid1,NULL,&Children,NULL);//Create main thread
if(ret1 == 0)
{
printf("Main Thread ok!\n");
sleep(20);
}
else{
printf("Thread failed!\n");
}
FCFS();
SJF();
cout<<"Please enter RR time:\n";//Request RR time
int rr;
scanf("%d",&rr);
RR(rr);
Priority();
return 0;
}
OK!此代码的运行结果如下(部分):
第一张图打印了一下虚拟PCB的部分内容:
第二张图片打印了FCFS调度算法运行结果:
第三张图片打印了SJF调度算法运行结果:
第四张图片打印了RR调度算法运行结果(部分):
第五张图片打印了Priority调度算法运行结果:
注意看每张图下面的两行数据,分别是不同算法对应的总的进程的等待时间以及平均等待时间的大小,印证了SJF算法通常是最少平均等待时间的调度算法
最后希望大家能够积极提建议,指出纰漏!