PAT A1017 Queueing at Bank (25 分) 模拟

60 篇文章 0 订阅

        题目大意:银行有K个窗口,给出N个人的到达时间和办理业务需要的时间,银行从8:00开始营业,求出每个在17:00前到达的人的平均等待时间。每个人的业务时间不能超过1h(事实上没有测试点对应这句话)。

       一开始是想把时间全部折算成从8:00开始计算的分钟的,但是这样到最后double和int很容易弄混,弄混了精度就丢失了,导致测试点5始终过不了,所以还是全部折算成从8:00开始计算的秒比较合适。

      然后就是所有人按到达时间排序,依次处理。首先找到最小空出时间的窗口,如果当前处理的人的到达时间小于最小空出时间,那么总的等待时间需要更新,最小空出时间窗口的信息需要更新为 freeAtTime += processTime;如果当前处理的人的到达时间大于等于最小空出时间,那么不需要等待,最小空出时间的窗口的信息更新为 freeAtTime = arriveTime + processTime。

AC代码如下:

#include <vector>
#include <algorithm>
#include <cstdio>

using namespace std;

int timeToSec(int hour, int min, int sec)
{
    return  hour * 3600 + min * 60 + sec - 8 * 3600;
}

struct customer
{
    int arriveTime;
    int processTime;
    bool operator <(const customer& other)
    {
        return this->arriveTime < other.arriveTime;
    }
};

const int MAXK = 110;
int freeAtTime[MAXK] = {0}; //从8:00开始计时

int main()
{
    int N, K;
    scanf("%d%d", &N, &K);
    vector<customer> v(N);
    for (int i = 0; i < N; ++i)
    {
        int hour, min, sec, processTime;
        scanf("%d:%d:%d %d", &hour, &min, &sec, &processTime);
        if(hour < 17 || (hour == 17 && min == 0 && sec == 0))
        {
            v[i].arriveTime = timeToSec(hour, min, sec);
            v[i].processTime = processTime <= 60? processTime * 60 : 60 * 60;
        }
        else
        {
            i--;
            N--;
        }
    }
    sort(v.begin(), v.begin() + N);
    double totalWaitTime = 0;
    for (int i = 0; i < N; ++i)
    {
        int minIndex = 0, minFreeTime = 0x7FFFFFFF;
        for (int j = 0; j < K; ++j)
        {
            if(freeAtTime[j] < minFreeTime)
            {
                minFreeTime = freeAtTime[j];
                minIndex = j;
            }
        }
        if(v[i].arriveTime < minFreeTime)
        {
            totalWaitTime += minFreeTime - v[i].arriveTime;
            freeAtTime[minIndex] += v[i].processTime;
        }
        else
            freeAtTime[minIndex] = v[i].arriveTime + v[i].processTime;
    }
    printf("%.1f", totalWaitTime / 60.0 / N);
    return 0;
}


 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值