习题8.1 银行排队问题之单队列多窗口服务

题目

假设银行有K个窗口提供服务,窗口前设一条黄线,所有顾客按到达时间在黄线后排成一条长龙。当有窗口空闲时,下一位顾客即去该窗口处理事务。当有多个窗口可选择时,假设顾客总是选择编号最小的窗口。
本题要求输出前来等待服务的N位顾客的平均等待时间、最长等待时间、最后完成时间,并且统计每个窗口服务了多少名顾客。

思路

具体实现思路,模仿了操作系统中的进程调度占用cpu的状态分析。注意完成时间,最后完成时间,一定是最后window数组中最长的那个。

代码

#include<stdio.h>
#include<stdlib.h>
#define N 1000
#define M 10
typedef struct consumer{
	int beganTime;
	int workTime;
}consumer;
int findMin(int x);
void sort(int low,int high);
int Quick(int low,int high);

consumer con[N];
int n,k,window[M],wait[N],windowCount[M];//window存储完成时间,wait存储等待时间,windowCount存储每个窗口的访问次数
void main(){
	int i,j,index;
	float sum=0.0;
	int maxW=0,Mtime=0;
	scanf("%d",&n);
	for(i=0;i<n;i++){
		scanf("%d %d",&con[i].beganTime,&con[i].workTime);
		if(con[i].workTime>60)
			con[i].workTime=60;
	}
	sort(0,n-1);//按先来后到顺序排序
	scanf("%d",&k);
	for(i=0;i<k;i++)//初始化window
		window[i]=0;
	for(i=0;i<n;i++)//初始化wait
		wait[i]=0;
	for(i=0;i<k;i++)
		windowCount[i]=0;

	for(i=0;i<n;i++){//核心
		index=findMin(i);
		windowCount[index]++;
		printf("index=%d\n",index);
		if(window[index]<=con[i].beganTime){
			window[index]=con[i].beganTime+con[i].workTime;
		}
		else{
			wait[i]=window[index]-con[i].beganTime;
			window[index]=window[index]+con[i].workTime;
		}

	}

	for(i=0;i<n;i++)
		if(wait[i]){
			sum+=wait[i];
			if(maxW<wait[i])
				maxW=wait[i];
		}
	printf("AvgWait=%.1f WaitMax=%d ",sum/n,maxW);
	for(i=0;i<k;i++)
		if(Mtime<window[i])
			Mtime=window[i];
	printf("Mtime=%d\n",Mtime);
	for(i=0;i<k;i++)
		printf(" %d",windowCount[i]);
	system("pause");
}
int findMin(int x){
	int i,index;
	int min=65534;
	for(i=0;i<k;i++){
		if(con[x].beganTime>=window[i])//此处先判断一下,是否有窗口可用,依据题目总是寻找最小编号的窗口先使用
			return i;
		else if(min>window[i]){
			min=window[i];
			index=i;
		}
	}
	if(min!=65534){
		return index;
	}else
		return -1;
}
void sort(int low,int high){
	int piv;
	if(low<high){
		piv=Quick(low,high);
		sort(low,piv-1);
		sort(piv+1,high);
	}
}
int Quick(int low,int high){
	consumer temp;
	temp=con[low];
	while(low < high){
		while(low<high && temp.beganTime<=con[high].beganTime)
			high--;
		con[low]=con[high];
		while(low<high && temp.beganTime>=con[low].beganTime)
			low++;
		con[high]=con[low];
	}
	con[low]=temp;
	return low;
}

总结

需要注意的是findMin函数中注释部分,缺少此步就容易出现最后窗口次数访问不符合答案的情况。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值