PAT 1014 Waiting in Line (30 分)(模拟)

题意

一个银行有n个窗口,每个窗口最多排m个人,多出去的人在黄线外等候,一共有k个人同时进入银行办理业务,每个人有一个办理业务所需要的时间,每个人会选择人数最少的窗口进行排队或者办理业务,若人数最少窗口相同的话选择序号最小的窗口。然后进行q次询问,询问编号为x的人办理完业务的时间为多少,银行每天8:00开门17:00关门,若在关门后办理业务输出sorry

思路

  1. 由于时间是从8点到17点所以,我们模拟时间来就可以了,用一个for循环来模拟时间,每一次判断排队第一个人办理业务的结束的时间是否为循环时间,若等于则将排第一个的人踢出,然后第二个人就变为第一个人开始办理业务,结束时间是当前循环时间加上他的办理时间
  2. 每个窗口的队伍可以用一个vector来模拟,第一个人可以用vector中的erase来去掉。
  3. 我们每次时间判断一下有没有队伍可以加入,如果有就去寻找一下人数最小的那个队伍去加入
  4. 有一点需要注意的是若开始办理的时间在17点之前(不包括17点)但是结束时间在17点或17点后,他也是算的而不能输出sorry
#include<bits/stdc++.h>
using namespace std;
struct node
{
    int id;
    int flag;
    int end;
    int con;
} a[1005];
vector<node>b[25];
queue<int>c;
int ans[1005];
int main()
{
    memset(ans,-1,sizeof(ans));
    int n,m,k,q;
    scanf("%d%d%d%d",&n,&m,&k,&q);
    for(int i=1; i<=k; i++)
    {
        a[i].id=i;
        scanf("%d",&a[i].con);
        int minn=m;
        int pos=0;
        for(int j=1; j<=n; j++)
        {
            if(minn>b[j].size())
            {
                minn=b[j].size();
                pos=j;
            }
        }
        if(pos&&b[pos].size()<m)
        {
            if(b[pos].size()==0)
            {
                a[i].flag=1;
                a[i].end=a[i].con;
            }
            b[pos].push_back(a[i]);
        }
        else
            c.push(i);
    }
    for(int i=0; i<540; i++)
    {
        int flag=0;
        for(int j=1; j<=n; j++)
        {
            if(b[j].size()&&b[j][0].end==i)
            {
                flag=1;
                ans[b[j][0].id]=i;
                b[j].erase(b[j].begin());
                if(b[j].size())
                    {
                        b[j][0].flag=1;
                        b[j][0].end=i+b[j][0].con;
                    }
            }
        }
        while(!c.empty()&&flag)
        {
            int minn=m;
            int pos=0;
            for(int j=1; j<=n; j++)
            {
                if(minn>b[j].size())
                {
                    minn=b[j].size();
                    pos=j;
                }
            }
            if(pos&&b[pos].size()<m)
            {
                b[pos].push_back(a[c.front()]);
                c.pop();
            }
            else
                break;
        }
    }
    for(int i=1; i<=n; i++)
        if(b[i].size()!=0)
        {
            if(b[i][0].flag==1)
            ans[b[i][0].id]=b[i][0].end;
        }
    while(q--)
    {
        int x;
        scanf("%d",&x);
        if(ans[x]!=-1)
            printf("%.2d:%.2d\n",ans[x]/60+8,ans[x]%60);
        else
            printf("Sorry\n");
    }
    return 0;
}



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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值